Source code of Windows XP (NT5)
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.

1161 lines
38 KiB

  1. /*************************************************************************/
  2. /* Copyright (C) 1999 Microsoft Corporation */
  3. /* File: MSMFBBtn.cpp */
  4. /* Description: Implementation of CMSMFBBtn Bitmap Button */
  5. /* Author: David Janecek */
  6. /*************************************************************************/
  7. #include "stdafx.h"
  8. #include "MSMFCnt.h"
  9. #include "MSMFBBtn.h"
  10. #include "ocidl.h" // Added by ClassView
  11. extern CComModule _Module;
  12. /////////////////////////////////////////////////////////////////////////////
  13. // CMSMFBBtn
  14. /*************************************************************************/
  15. /* Function: CMSMFBBtn */
  16. /*************************************************************************/
  17. CMSMFBBtn::CMSMFBBtn(){
  18. Init();
  19. for(INT i = 0; i < cgMaxBtnStates; i++){
  20. m_pBitmap[i] = new CBitmap;
  21. }/* end of for loop */
  22. }/* end of function CMSMFBBtn */
  23. /*************************************************************************/
  24. /* Function: Init */
  25. /* Description: Initializes variable states. */
  26. /*************************************************************************/
  27. void CMSMFBBtn::Init(){
  28. m_nEntry = BtnState::Static;
  29. m_fDirty = true; // to refresh text property, font etc.
  30. m_uiFontSize = 10;
  31. m_bstrTextValue = L"";
  32. m_bstrFontFace = L"Arial";
  33. m_bstrFontStyle = L"Normal";
  34. m_clrBackColor = ::GetSysColor(COLOR_BTNFACE);
  35. m_clrColorActive = 0x00ff0000; // blue
  36. m_clrColorStatic = 0x00000000; // black
  37. m_clrColorHover = 0x00ff0000; // blue
  38. m_clrColorPush = 0x00ffffff; // white
  39. m_clrColorDisable = 0x00808080; // grey
  40. m_dwButtonClickStamp = 0;
  41. #if 0 // used for getting the windowed case working DJ
  42. m_bWindowOnly = TRUE;
  43. #endif
  44. }/* end of function Init */
  45. /*************************************************************************/
  46. /* Function: ~CMSMFBBtn */
  47. /* Description: Cleanup the bitmap and pallete arrays, unload resource */
  48. /* DLL. */
  49. /*************************************************************************/
  50. CMSMFBBtn::~CMSMFBBtn(){
  51. ATLTRACE(TEXT("In the BUTTON Object destructor!\n"));
  52. for(INT i = 0; i < cgMaxBtnStates; i++){
  53. if (m_pBitmap[i]){
  54. delete m_pBitmap[i];
  55. m_pBitmap[i] = NULL;
  56. }/* end of if statement */
  57. //CComBSTR m_bstrFilename[..] should get destructed on the stack
  58. }/* end of for loop */
  59. Init();
  60. }/* end of function ~CMSMFBBtn */
  61. /*************************************************************************/
  62. /* Function: OnDraw */
  63. /* Description: Does the basic drawing */
  64. /*************************************************************************/
  65. HRESULT CMSMFBBtn::OnDraw(ATL_DRAWINFO& di){
  66. USES_CONVERSION;
  67. RECT& rc = *(RECT*)di.prcBounds;
  68. HRESULT hr = S_OK;
  69. if (m_pBitmap[m_nEntry]){
  70. BOOL bRet;
  71. HPALETTE hNewPal = m_pBitmap[m_nEntry]->GetPal();
  72. if (::IsWindow(m_hWnd)){ // in othere words not windowless
  73. CBitmap::SelectRelizePalette(di.hdcDraw, hNewPal);
  74. }/* end of if statement */
  75. if (::IsWindow(m_hWnd) && m_blitType != DISABLE) {
  76. COLORREF clr;
  77. ::OleTranslateColor (m_clrBackColor, hNewPal, &clr);
  78. // fill background of specific color
  79. HBRUSH hbrBack = ::CreateSolidBrush(clr);
  80. if(NULL == hbrBack){
  81. hr = E_UNEXPECTED;
  82. return hr;
  83. }/* end of if statement */
  84. //::FillRect(hdc, &rcClient, hbrBack);
  85. ::FillRect(di.hdcDraw, (LPRECT)di.prcBounds, hbrBack);
  86. ::DeleteObject(hbrBack);
  87. }
  88. bRet = m_pBitmap[m_nEntry]->PaintTransparentDIB(di.hdcDraw, (LPRECT) di.prcBounds,
  89. (LPRECT) di.prcBounds);
  90. if (m_fDirty)
  91. {
  92. SetTextProperties();
  93. }
  94. if(m_bstrTextValue.Length() > 0){
  95. // draw text only if needed
  96. hr = m_cText.Write(di.hdcDraw, rc, m_bstrTextValue);
  97. }/* end of if statement */
  98. hr = GetFocus();
  99. // THIS ASSUMES WE ARE REPAINTING THE WHOLE CONTROL
  100. // WHICH IS WHAT ATL AT THIS INCARNATION DOES
  101. if(S_OK == hr){
  102. ::DrawFocusRect(di.hdcDraw, (LPRECT)di.prcBounds);
  103. }/* end of if statement */
  104. if(!bRet){
  105. hr = E_UNEXPECTED;
  106. }/* end of if statement */
  107. }/* end of if statement */
  108. return (hr);
  109. }/* end of function OnDraw */
  110. /*************************************************************************/
  111. /* Function: SetTextProperties */
  112. /* Description: Set the properties for the CText object. */
  113. /*************************************************************************/
  114. HRESULT CMSMFBBtn::SetTextProperties()
  115. {
  116. HRESULT hr = S_OK;
  117. m_cText.SetFontFace(m_bstrFontFace);
  118. m_cText.SetFontSize(m_uiFontSize);
  119. m_cText.SetFontStyle(m_bstrFontStyle);
  120. m_cText.SetFixedSizeFont(true);
  121. // set the font color based on the current state
  122. OLE_COLOR clrColorCurrent = m_clrColorStatic;
  123. switch(m_nEntry)
  124. {
  125. case(BtnState::Static):
  126. clrColorCurrent = m_clrColorStatic;
  127. break;
  128. case(BtnState::Hover):
  129. clrColorCurrent = m_clrColorHover;
  130. break;
  131. case(BtnState::Active):
  132. clrColorCurrent = m_clrColorActive;
  133. break;
  134. case(BtnState::Push):
  135. clrColorCurrent = m_clrColorPush;
  136. break;
  137. case(BtnState::Disabled):
  138. clrColorCurrent = m_clrColorDisable;
  139. break;
  140. }
  141. // translate OLE_COLOR to COLORREF
  142. COLORREF crCurrentState;
  143. hr = OleTranslateColor(clrColorCurrent, CBitmap::GetSuperPal(), &crCurrentState);
  144. if (FAILED(hr))
  145. {
  146. crCurrentState = GetSysColor(COLOR_WINDOWTEXT);
  147. }
  148. m_cText.SetTextColor(crCurrentState);
  149. m_fDirty = false;
  150. return hr;
  151. }
  152. STDMETHODIMP CMSMFBBtn::get_TextWidth(long *pVal)
  153. {
  154. // special case early return
  155. if (m_bstrTextValue.Length() == 0)
  156. {
  157. *pVal = 0;
  158. return S_OK;
  159. }
  160. // get the current window or the window of its parent
  161. HWND hwnd = GetWindow();
  162. HDC hdc = ::GetWindowDC(hwnd);
  163. // normalize to pixel coord as required by the container
  164. SetMapMode(hdc, MM_TEXT);
  165. if (m_fDirty)
  166. {
  167. SetTextProperties();
  168. }
  169. SIZE size;
  170. m_cText.GetTextWidth(hdc, m_bstrTextValue, &size);
  171. *pVal = size.cx;
  172. ::ReleaseDC(hwnd, hdc); // do not forget to free DC
  173. return S_OK;
  174. }
  175. STDMETHODIMP CMSMFBBtn::get_TextHeight(long *pVal)
  176. {
  177. // get the current window or the window of its parent
  178. HWND hwnd = GetWindow();
  179. HDC hdc = ::GetWindowDC(hwnd);
  180. if(NULL == hdc){
  181. return(E_UNEXPECTED);
  182. }/* end of if statement */
  183. // normalize to pixel coord as required by the container
  184. SetMapMode(hdc, MM_TEXT);
  185. if (m_fDirty)
  186. {
  187. SetTextProperties();
  188. }
  189. SIZE size;
  190. m_cText.GetTextWidth(hdc, m_bstrTextValue, &size);
  191. *pVal = size.cy;
  192. ::ReleaseDC(hwnd, hdc); // do not forget to free DC
  193. return S_OK;
  194. }
  195. /*************************************************************************/
  196. /* Function: get_ColorPush */
  197. /* Description: return the ColorPush property. */
  198. /*************************************************************************/
  199. STDMETHODIMP CMSMFBBtn::get_ColorPush(OLE_COLOR *pColor)
  200. {
  201. if (!pColor)
  202. {
  203. return E_POINTER;
  204. }
  205. *pColor = m_clrColorPush;
  206. return S_OK;
  207. }
  208. /*************************************************************************/
  209. /* Function: put_ColorPush */
  210. /* Description: set the ColorPush property. This is the color of text */
  211. /* in the Push state. */
  212. /*************************************************************************/
  213. STDMETHODIMP CMSMFBBtn::put_ColorPush(OLE_COLOR clrColor)
  214. {
  215. m_clrColorPush = clrColor;
  216. if (m_nEntry == BtnState::Push)
  217. {
  218. m_fDirty = true;
  219. }
  220. return S_OK;
  221. }
  222. /*************************************************************************/
  223. /* Function: get_ColorHover */
  224. /* Description: return the ColorHover property. */
  225. /*************************************************************************/
  226. STDMETHODIMP CMSMFBBtn::get_ColorHover(OLE_COLOR *pColor)
  227. {
  228. if (!pColor)
  229. {
  230. return E_POINTER;
  231. }
  232. *pColor = m_clrColorHover;
  233. return S_OK;
  234. }
  235. /*************************************************************************/
  236. /* Function: put_ColorHover */
  237. /* Description: set the ColorHover property. This is the color of text */
  238. /* in the Hover state. */
  239. /*************************************************************************/
  240. STDMETHODIMP CMSMFBBtn::put_ColorHover(OLE_COLOR clrColor)
  241. {
  242. m_clrColorHover = clrColor;
  243. if (m_nEntry == BtnState::Hover)
  244. {
  245. m_fDirty = true;
  246. }
  247. return S_OK;
  248. }
  249. /*************************************************************************/
  250. /* Function: get_ColorStatic */
  251. /* Description: return the ColorStatic property. */
  252. /*************************************************************************/
  253. STDMETHODIMP CMSMFBBtn::get_ColorStatic(OLE_COLOR *pColor)
  254. {
  255. if (!pColor)
  256. {
  257. return E_POINTER;
  258. }
  259. *pColor = m_clrColorStatic;
  260. return S_OK;
  261. }
  262. /*************************************************************************/
  263. /* Function: put_ColorPush */
  264. /* Description: set the ColorPush property. This is the color of text */
  265. /* in the Static (normal) state. */
  266. /*************************************************************************/
  267. STDMETHODIMP CMSMFBBtn::put_ColorStatic(OLE_COLOR clrColor)
  268. {
  269. m_clrColorStatic = clrColor;
  270. if (m_nEntry == BtnState::Static)
  271. {
  272. m_fDirty = true;
  273. }
  274. return S_OK;
  275. }
  276. /*************************************************************************/
  277. /* Function: get_ColorDisable */
  278. /* Description: return the ColorDisable property. */
  279. /*************************************************************************/
  280. STDMETHODIMP CMSMFBBtn::get_ColorDisable(OLE_COLOR *pColor)
  281. {
  282. if (!pColor)
  283. {
  284. return E_POINTER;
  285. }
  286. *pColor = m_clrColorDisable;
  287. return S_OK;
  288. }
  289. /*************************************************************************/
  290. /* Function: put_ColorDisable */
  291. /* Description: set the ColorDisable property. This is the color of text */
  292. /* in the Disabled state. */
  293. /*************************************************************************/
  294. STDMETHODIMP CMSMFBBtn::put_ColorDisable(OLE_COLOR clrColor)
  295. {
  296. m_clrColorDisable = clrColor;
  297. if (m_nEntry == BtnState::Disabled)
  298. {
  299. m_fDirty = true;
  300. }
  301. return S_OK;
  302. }
  303. /*************************************************************************/
  304. /* Function: get_ColorActive */
  305. /* Description: return the ColorActive property. */
  306. /*************************************************************************/
  307. STDMETHODIMP CMSMFBBtn::get_ColorActive(OLE_COLOR *pColor)
  308. {
  309. if (!pColor)
  310. {
  311. return E_POINTER;
  312. }
  313. *pColor = m_clrColorActive;
  314. return S_OK;
  315. }
  316. /*************************************************************************/
  317. /* Function: put_ColorActive */
  318. /* Description: set the ColorActive property. This is the color of text */
  319. /* in the Active state. */
  320. /*************************************************************************/
  321. STDMETHODIMP CMSMFBBtn::put_ColorActive(OLE_COLOR clrColor)
  322. {
  323. m_clrColorActive = clrColor;
  324. if (m_nEntry == BtnState::Active)
  325. {
  326. m_fDirty = true;
  327. }
  328. return S_OK;
  329. }
  330. /*************************************************************************/
  331. /* Function: get_FontSize */
  332. /* Description: return the FontSize property. */
  333. /*************************************************************************/
  334. STDMETHODIMP CMSMFBBtn::get_FontSize(long *pVal)
  335. {
  336. if (!pVal)
  337. {
  338. return E_POINTER;
  339. }
  340. *pVal = m_uiFontSize;
  341. return S_OK;
  342. }
  343. /*************************************************************************/
  344. /* Function: put_FontSize */
  345. /* Description: set the FontSize property, in pt. */
  346. /*************************************************************************/
  347. STDMETHODIMP CMSMFBBtn::put_FontSize(long lSize)
  348. {
  349. if ((UINT)lSize != m_uiFontSize)
  350. {
  351. m_uiFontSize = (UINT)lSize;
  352. m_fDirty = true;
  353. }
  354. return S_OK;
  355. }
  356. /*************************************************************************/
  357. /* Function: get_Text */
  358. /* Description: return the Text that is displayed in the control. */
  359. /*************************************************************************/
  360. STDMETHODIMP CMSMFBBtn::get_Text(BSTR *pText)
  361. {
  362. if (!pText)
  363. {
  364. return E_POINTER;
  365. }
  366. *pText = m_bstrTextValue.Copy();
  367. return S_OK;
  368. }
  369. /*************************************************************************/
  370. /* Function: put_Text */
  371. /* Description: set the text to be displayed in the control. */
  372. /*************************************************************************/
  373. STDMETHODIMP CMSMFBBtn::put_Text(BSTR wsText)
  374. {
  375. if (_wcsicmp(m_bstrTextValue, wsText) != 0)
  376. {
  377. m_bstrTextValue = wsText;
  378. FireViewChange();
  379. }
  380. return S_OK;
  381. }
  382. /*************************************************************************/
  383. /* Function: get_FontFace */
  384. /* Description: return the FontFace property. */
  385. /*************************************************************************/
  386. STDMETHODIMP CMSMFBBtn::get_FontFace(BSTR *pFontFace)
  387. {
  388. if (!pFontFace)
  389. {
  390. return E_POINTER;
  391. }
  392. *pFontFace = m_bstrFontFace.Copy();
  393. return S_OK;
  394. }
  395. /*************************************************************************/
  396. /* Function: put_FontFace */
  397. /* Description: set the FontFace property. */
  398. /*************************************************************************/
  399. STDMETHODIMP CMSMFBBtn::put_FontFace(BSTR wsFontFace)
  400. {
  401. if (_wcsicmp(m_bstrFontFace, wsFontFace) != 0)
  402. {
  403. m_bstrFontFace = wsFontFace;
  404. m_fDirty = true;
  405. }
  406. return S_OK;
  407. }
  408. /*************************************************************************/
  409. /* Function: get_FontStyle */
  410. /* Description: return the FontSize property. */
  411. /*************************************************************************/
  412. STDMETHODIMP CMSMFBBtn::get_FontStyle(BSTR *pFontStyle)
  413. {
  414. if (!pFontStyle)
  415. {
  416. return E_POINTER;
  417. }
  418. *pFontStyle = m_bstrFontStyle.Copy();
  419. return S_OK;
  420. }
  421. /*************************************************************************/
  422. /* Function: put_FontStyle */
  423. /* Description: set the FontStyle property. The style string should */
  424. /* contain either "Normal", or concatenation of one or more strings of: */
  425. /* "Bold", "Italic", "Underline", "Strikeout". Default is "Normal". */
  426. /*************************************************************************/
  427. STDMETHODIMP CMSMFBBtn::put_FontStyle(BSTR wsFontStyle)
  428. {
  429. if (_wcsicmp(m_bstrFontStyle, wsFontStyle) != 0)
  430. {
  431. m_bstrFontStyle = wsFontStyle;
  432. m_fDirty = true;
  433. }
  434. return S_OK;
  435. }
  436. /*************************************************************************/
  437. /* Function: get_ImageStatic */
  438. /*************************************************************************/
  439. STDMETHODIMP CMSMFBBtn::get_ImageStatic(BSTR *pstrFilename){
  440. *pstrFilename = m_bstrFilename[BtnState::Static].Copy();
  441. return S_OK;
  442. }/* end of function get_ImageStatic */
  443. /*************************************************************************/
  444. /* Function: put_ImageStatic */
  445. /*************************************************************************/
  446. STDMETHODIMP CMSMFBBtn::put_ImageStatic(BSTR strFilename){
  447. if (!m_bstrFilename[BtnState::Disabled])
  448. PutImage(strFilename, BtnState::Disabled);
  449. return (PutImage(strFilename, BtnState::Static));
  450. }/* end of function put_ImageStatic */
  451. /*************************************************************************/
  452. /* Function: get_ImageHover */
  453. /*************************************************************************/
  454. STDMETHODIMP CMSMFBBtn::get_ImageHover(BSTR *pstrFilename){
  455. *pstrFilename = m_bstrFilename[BtnState::Hover].Copy();
  456. return S_OK;
  457. }/* end of function get_ImageHover */
  458. /*************************************************************************/
  459. /* Function: put_ImageHover */
  460. /*************************************************************************/
  461. STDMETHODIMP CMSMFBBtn::put_ImageHover(BSTR strFilename){
  462. return (PutImage(strFilename, BtnState::Hover));
  463. }/* end of function put_ImageHover */
  464. /*************************************************************************/
  465. /* Function: get_ImagePush */
  466. /*************************************************************************/
  467. STDMETHODIMP CMSMFBBtn::get_ImagePush(BSTR *pstrFilename){
  468. *pstrFilename = m_bstrFilename[BtnState::Push].Copy();
  469. return S_OK;
  470. }/* end of function get_ImagePush */
  471. /*************************************************************************/
  472. /* Function: put_ImagePush */
  473. /*************************************************************************/
  474. STDMETHODIMP CMSMFBBtn::put_ImagePush(BSTR strFilename){
  475. return (PutImage(strFilename, BtnState::Push));
  476. }/* end of function put_ImagePush */
  477. /*************************************************************************/
  478. /* Function: get_ImageDisabled */
  479. /*************************************************************************/
  480. STDMETHODIMP CMSMFBBtn::get_ImageDisabled(BSTR *pstrFilename){
  481. *pstrFilename = m_bstrFilename[BtnState::Disabled].Copy();
  482. return S_OK;
  483. }/* end of function get_ImagePush */
  484. /*************************************************************************/
  485. /* Function: put_ImageDisabled */
  486. /*************************************************************************/
  487. STDMETHODIMP CMSMFBBtn::put_ImageDisabled(BSTR strFilename){
  488. return (PutImage(strFilename, BtnState::Disabled));
  489. }/* end of function put_ImagePush */
  490. /*************************************************************************/
  491. /* Function: get_ImageActive */
  492. /*************************************************************************/
  493. STDMETHODIMP CMSMFBBtn::get_ImageActive(BSTR *pstrFilename){
  494. *pstrFilename = m_bstrFilename[BtnState::Active].Copy();
  495. return S_OK;
  496. }/* end of function get_ImagePush */
  497. /*************************************************************************/
  498. /* Function: put_ImageActive */
  499. /*************************************************************************/
  500. STDMETHODIMP CMSMFBBtn::put_ImageActive(BSTR strFilename){
  501. return (PutImage(strFilename, BtnState::Active));
  502. }/* end of function put_ImagePush */
  503. /*************************************************************************/
  504. /* Function: PutImage */
  505. /* Description: Reads the DIB file (from file or resource) into a DIB, */
  506. /* updates palette and rects of the internal bitmap. */
  507. /* Also forces redraw if changing the active image. */
  508. /*************************************************************************/
  509. HRESULT CMSMFBBtn::PutImage(BSTR strFilename, int nEntry){
  510. USES_CONVERSION;
  511. HRESULT hr = S_OK;
  512. m_bstrFilename[nEntry] = strFilename;
  513. TCHAR strBuffer[MAX_PATH] = TEXT("\0");
  514. bool fGrayOut = false;
  515. if(BtnState::Disabled == nEntry){
  516. fGrayOut = gcfGrayOut;
  517. }/* end of if statement */
  518. hr = m_pBitmap[nEntry]->PutImage(strFilename, m_hRes, TRUE, m_blitType, NORMAL);
  519. if(FAILED(hr)){
  520. return(hr);
  521. }/* end of if statement */
  522. if(nEntry == m_nEntry ){
  523. // we are updating image that is being used, refresh it
  524. ATLTRACE2(atlTraceWindowing, 20, TEXT("Redrawing the image\n"));
  525. InvalidateRgn(); // our helper function
  526. }/* end of if statement */
  527. return(hr);
  528. }/* end of function PutImage */
  529. /*************************************************************************/
  530. /* Function: OnButtonDown */
  531. /* Description: Handles when buttons is selected. Captures the mouse */
  532. /* movents (supported for windowless, via interfaces). */
  533. /*************************************************************************/
  534. LRESULT CMSMFBBtn::OnButtonDown(UINT, WPARAM wParam, LPARAM lParam, BOOL& bHandled){
  535. if (m_nEntry == BtnState::Disabled){
  536. return 0;
  537. }/* end of if statement */
  538. LONG xPos = GET_X_LPARAM(lParam);
  539. LONG yPos = GET_Y_LPARAM(lParam);
  540. if(PtOnButton(xPos, yPos)){
  541. // we are really on the buttons bitmap and we pushed it
  542. if(BtnState::Hover != m_nEntry){
  543. // in hover case we already have captured the mouse, so do not do
  544. // that again
  545. SetCapture(true); // capture the mouse messages
  546. }/* end of if statement */
  547. SetButtonState(BtnState::Push);
  548. }/* end of if statement */
  549. Fire_OnMouseDown();
  550. return 0;
  551. }/* end of function OnButtonDown */
  552. /*************************************************************************/
  553. /* Function: OnButtonUp */
  554. /* Description: Releases the capture, updates the button visual state, */
  555. /* and if release on the buttons image fire the event. */
  556. /*************************************************************************/
  557. LRESULT CMSMFBBtn::OnButtonUp(UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled){
  558. LONG lRes = 0;
  559. DWORD dwTick = ::GetTickCount();
  560. ATLTRACE(TEXT("old stamp %d\n"), m_dwButtonClickStamp);
  561. ATLTRACE(TEXT("new stamp %d\n"), dwTick);
  562. if ( dwTick - m_dwButtonClickStamp <= ::GetDoubleClickTime()) {
  563. uMsg = WM_LBUTTONDBLCLK;
  564. OnDblClick(uMsg, wParam, lParam, bHandled);
  565. return 0;
  566. }
  567. else
  568. m_dwButtonClickStamp = dwTick;
  569. if (m_nEntry == BtnState::Disabled){
  570. ForwardWindowMessage(WM_USER_FOCUS, (WPARAM) m_hWnd, 0, lRes);
  571. ForwardWindowMessage(WM_USER_ENDHELP, (WPARAM) m_hWnd, 0, lRes);
  572. return lRes;
  573. }/* end of if statement */
  574. LONG xPos = GET_X_LPARAM(lParam);
  575. LONG yPos = GET_Y_LPARAM(lParam);
  576. bool bOnButtonImage = PtOnButton(xPos, yPos);
  577. bool bFire = (m_nEntry == BtnState::Push);
  578. if(bOnButtonImage){
  579. SetButtonState(BtnState::Static); //change to static even
  580. SetCapture(false); // release the capture of the mouse messages
  581. }
  582. else {
  583. SetButtonState(BtnState::Static);
  584. // do it only when we do not hower, if we hower, then keep the capture
  585. SetCapture(false); // release the capture of the mouse messages
  586. }/* end of if statement */
  587. if (bFire){
  588. if(bOnButtonImage){
  589. Fire_OnClick();
  590. }/* end of if statement */
  591. }/* end of if statement */
  592. Fire_OnMouseUp();
  593. ForwardWindowMessage(WM_USER_FOCUS, (WPARAM) m_hWnd, 0, lRes);
  594. ForwardWindowMessage(WM_USER_ENDHELP, (WPARAM) m_hWnd, 0, lRes);
  595. return lRes;
  596. }/* end of function OnButtonUp */
  597. /*************************************************************************/
  598. /* Function: OnDblClick */
  599. /* Description: Releases the capture, updates the button visual state, */
  600. /* and if release on the buttons image fire the event. */
  601. /*************************************************************************/
  602. LRESULT CMSMFBBtn::OnDblClick(UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled){
  603. LONG lRes = 0;
  604. if (m_nEntry == BtnState::Disabled){
  605. ForwardWindowMessage(WM_USER_FOCUS, (WPARAM) m_hWnd, 0, lRes);
  606. return lRes;
  607. }/* end of if statement */
  608. LONG xPos = GET_X_LPARAM(lParam);
  609. LONG yPos = GET_Y_LPARAM(lParam);
  610. bool bOnButtonImage = PtOnButton(xPos, yPos);
  611. if(bOnButtonImage){
  612. SetButtonState(BtnState::Static); //change to static even
  613. SetCapture(false); // release the capture of the mouse messages
  614. }
  615. else {
  616. SetButtonState(BtnState::Static);
  617. // do it only when we do not hower, if we hower, then keep the capture
  618. SetCapture(false); // release the capture of the mouse messages
  619. }/* end of if statement */
  620. if(bOnButtonImage){
  621. Fire_OnDblClick();
  622. }/* end of if statement */
  623. ForwardWindowMessage(WM_USER_FOCUS, (WPARAM) m_hWnd, 0, lRes);
  624. return lRes;
  625. }/* end of function OnDblClick */
  626. /*************************************************************************/
  627. /* Function: OnMouseMove */
  628. /* Description: Check if we were captured/pushed the do not do much, */
  629. /* otherwise do the hit detection and see if we are in static or hower */
  630. /* state. */
  631. /*************************************************************************/
  632. LRESULT CMSMFBBtn::OnMouseMove(UINT, WPARAM wParam, LPARAM lParam, BOOL& bHandled){
  633. if (m_nEntry == BtnState::Disabled)
  634. return 0;
  635. LONG xPos = GET_X_LPARAM(lParam);
  636. LONG yPos = GET_Y_LPARAM(lParam);
  637. if (m_nEntry != BtnState::Push){
  638. if(PtOnButton(xPos, yPos)){
  639. if(BtnState::Hover != m_nEntry || S_OK != GetCapture()){
  640. SetCapture(true); // capture the mouse messages
  641. SetButtonState(BtnState::Hover);
  642. }/* end of if statement */
  643. }
  644. else {
  645. if(BtnState::Static != m_nEntry){
  646. SetCapture(false); // release the capture of the mouse messages
  647. SetButtonState(BtnState::Static);
  648. }/* end of if statement */
  649. }/* end of if statement */
  650. }/* end of if statement */
  651. return 0;
  652. }/* end of function OnMouseMove */
  653. /*************************************************************************/
  654. /* Function: OnSetFocus */
  655. /* Description: If we are in disabled state SetFocus(false) */
  656. /*************************************************************************/
  657. LRESULT CMSMFBBtn::OnSetFocus(UINT msg, WPARAM wParam, LPARAM lParam, BOOL& bHandled){
  658. if (m_nEntry == BtnState::Disabled){
  659. if(GetFocus() == S_OK){
  660. SetFocus(false);
  661. }/* end of if statement */
  662. FireViewChange();
  663. return(-1);
  664. }/* end of if statement */
  665. FireViewChange();
  666. return 0;
  667. }/* end of function OnSetFocus */
  668. /*************************************************************************/
  669. /* Function: OnKillFocus */
  670. /* Description: If we are in disabled state SetFocus(false) */
  671. /*************************************************************************/
  672. LRESULT CMSMFBBtn::OnKillFocus(UINT msg, WPARAM wParam, LPARAM lParam, BOOL& bHandled){
  673. FireViewChange();
  674. return 0;
  675. }/* end of function OnKillFocus */
  676. /*************************************************************************/
  677. /* Function: PtOnButton */
  678. /* Description: Uses helper to do the same. */
  679. /*************************************************************************/
  680. bool CMSMFBBtn::PtOnButton(LONG x, LONG y){
  681. POINT pos = {x, y};
  682. return(PtOnButton(pos));
  683. }/* end of function PtOnButton */
  684. /*************************************************************************/
  685. /* Function: PtOnButton */
  686. /* Description: Determines if the point is located on the button. */
  687. /* TODO: Needs to be modified when we will handle transparent color. */
  688. /*************************************************************************/
  689. bool CMSMFBBtn::PtOnButton(POINT pos){
  690. RECT rc;
  691. bool bRet = false;
  692. if(m_bWndLess){
  693. rc = m_rcPos;
  694. }
  695. else {
  696. if(!::IsWindow(m_hWnd)){
  697. return(bRet);
  698. }/* end of if statement */
  699. ::GetClientRect(m_hWnd, &rc);
  700. }/* end of if statement */
  701. bRet = PtInRect(&rc, pos) ? true : false;
  702. //TODO: Add also if we are on bitmap itsels possibly
  703. #ifdef _DEBUG
  704. if(bRet)
  705. ATLTRACE2(atlTraceWindowing, 20, TEXT("Point x = %d y = %d in Rect left = %d top %d right %d bottom %d\n"),
  706. pos.x, pos.y, m_rcPos.left, m_rcPos.top, m_rcPos.right, m_rcPos.bottom);
  707. else
  708. ATLTRACE2(atlTraceWindowing, 20, TEXT("Point x = %d y = %d NOT ON RECT Rect left = %d top %d right %d bottom %d\n"),
  709. pos.x, pos.y, m_rcPos.left, m_rcPos.top, m_rcPos.right, m_rcPos.bottom);
  710. #endif
  711. return(bRet);
  712. }/* end of function PtOnButton */
  713. /*************************************************************************/
  714. /* Function: OnKeyDown */
  715. /* Description: Depresses the button. */
  716. /*************************************************************************/
  717. LRESULT CMSMFBBtn::OnKeyDown(UINT uMsg, WPARAM wParam, LPARAM lParam,
  718. BOOL& bHandled){
  719. bHandled = FALSE;
  720. LONG lRes = 0;
  721. if (m_nEntry == BtnState::Disabled){
  722. return 0;
  723. }/* end of if statement */
  724. switch(wParam){
  725. case VK_RETURN:
  726. case VK_SPACE:
  727. SetButtonState(BtnState::Push);
  728. break;
  729. }/* end of if statement */
  730. return(lRes);
  731. }/* end of function OnKeyDown */
  732. /*************************************************************************/
  733. /* Function: OnKeyUp */
  734. /* Description: Distrubutes the keyboard messages properly. */
  735. /*************************************************************************/
  736. LRESULT CMSMFBBtn::OnKeyUp(UINT uMsg, WPARAM wParam, LPARAM lParam,
  737. BOOL& bHandled){
  738. bHandled = FALSE;
  739. LONG lRes = 0;
  740. if (m_nEntry == BtnState::Disabled){
  741. return 0;
  742. }/* end of if statement */
  743. switch(wParam){
  744. case VK_RETURN:
  745. case VK_SPACE:
  746. Fire_OnClick();
  747. SetButtonState(BtnState::Static);
  748. break;
  749. }/* end of if statement */
  750. return(lRes);
  751. }/* end of function OnKeyUp */
  752. /*************************************************************************/
  753. /* Function: OnSize */
  754. /* Description: Invalidate region since size has changed */
  755. /*************************************************************************/
  756. LRESULT CMSMFBBtn::OnSize(UINT uMsg, WPARAM wParam, LPARAM lParam,
  757. BOOL& bHandled){
  758. bHandled = FALSE;
  759. InvalidateRgn();
  760. return 0;
  761. }
  762. /*************************************************************************/
  763. /* Function: OnDispChange */
  764. /* Description: Forwards this message to all the controls. */
  765. /*************************************************************************/
  766. LRESULT CMSMFBBtn::OnDispChange(UINT uMsg, WPARAM wParam, LPARAM lParam,
  767. BOOL& bHandled){
  768. LONG lRes =0;
  769. long cBitsPerPixel = (long)wParam;
  770. long cxScreen = LOWORD(lParam);
  771. long cyScreen = HIWORD(lParam);
  772. for (int i=0; i<cgMaxBtnStates; i++) {
  773. if (m_pBitmap[i])
  774. m_pBitmap[i]->OnDispChange(cBitsPerPixel, cxScreen, cyScreen);
  775. }
  776. return(lRes);
  777. }/* end of function OnDispChange */
  778. /*************************************************************************/
  779. /* Function: SetButtonState */
  780. /* Description: Sets the button states forces redraw. */
  781. /*************************************************************************/
  782. HRESULT CMSMFBBtn::SetButtonState(BtnState btnState){
  783. HRESULT hr = S_OK;
  784. bool fRedraw = false;
  785. if(btnState != m_nEntry ){
  786. fRedraw = true;
  787. }/* end of if statement */
  788. m_nEntry = btnState;
  789. if(fRedraw){
  790. if (m_nEntry == BtnState::Disabled){
  791. SetFocus(false); // disable the focus
  792. SetCapture(false);
  793. }/* end of if statement */
  794. // we are updating image that is being used, refresh it
  795. ATLTRACE2(atlTraceWindowing, 20, TEXT("Redrawing the image\n"));
  796. m_fDirty = true; // to force an update of font color
  797. FireViewChange(); // update the display
  798. //InvalidateRgn(); // our helper function
  799. }/* end of if statement */
  800. return(hr);
  801. }/* end of function SetButtonState */
  802. /*************************************************************************/
  803. /* Function: About */
  804. /* Description: Displays the AboutBox */
  805. /*************************************************************************/
  806. STDMETHODIMP CMSMFBBtn::About(){
  807. HRESULT hr = S_OK;
  808. const INT ciMaxBuffSize = MAX_PATH; // enough for the text
  809. TCHAR strBuffer[ciMaxBuffSize];
  810. TCHAR strBufferAbout[ciMaxBuffSize];
  811. if(!::LoadString(_Module.m_hInstResource, IDS_BTN_ABOUT, strBuffer, ciMaxBuffSize)){
  812. hr = E_UNEXPECTED;
  813. return(hr);
  814. }/* end of if statement */
  815. if(!::LoadString(_Module.m_hInstResource, IDS_ABOUT, strBufferAbout, ciMaxBuffSize)){
  816. hr = E_UNEXPECTED;
  817. return(hr);
  818. }/* end of if statement */
  819. ::MessageBox(::GetFocus(), strBuffer, strBufferAbout, MB_OK);
  820. return (hr);
  821. }/* end of function About */
  822. /*************************************************************/
  823. /* Function: get_Disable */
  824. /* Description: Returns OLE-BOOL if disabled or enabled. */
  825. /*************************************************************/
  826. STDMETHODIMP CMSMFBBtn::get_Disable(VARIANT_BOOL *pVal){
  827. *pVal = BtnState::Disabled == m_nEntry ? VARIANT_TRUE : VARIANT_FALSE;
  828. return S_OK;
  829. }/* end of function get_Disable */
  830. /*************************************************************/
  831. /* Function: put_Disable */
  832. /* Description: Disable or enable the buttons (disabled */
  833. /* are greyed out and do not except mouse clicks). */
  834. /*************************************************************/
  835. STDMETHODIMP CMSMFBBtn::put_Disable(VARIANT_BOOL newVal){
  836. // TODO: Right Now We Get Restored Automatically into Static state
  837. // we could detect the mouse and see if we are in static
  838. // or hower state
  839. BtnState btnSt = VARIANT_FALSE == newVal ? BtnState::Static : BtnState::Disabled;
  840. HRESULT hr = SetButtonState(btnSt);
  841. return (hr);
  842. }/* end of function put_Disable */
  843. /*************************************************************/
  844. /* Function: get_BtnState */
  845. /* Description: Gets current button state. */
  846. /*************************************************************/
  847. STDMETHODIMP CMSMFBBtn::get_BtnState(long *pVal){
  848. *pVal = (long) m_nEntry;
  849. return S_OK;
  850. }/* end of function get_BtnState */
  851. /*************************************************************/
  852. /* Function: put_BtnState */
  853. /* Description: Sets the button state manually. */
  854. /*************************************************************/
  855. STDMETHODIMP CMSMFBBtn::put_BtnState(long newVal){
  856. HRESULT hr = SetButtonState((BtnState)newVal);
  857. return(hr);
  858. }/* end of function put_BtnState */
  859. /*************************************************************/
  860. /* Name: SetObjectRects */
  861. /* Description: Update tooltip rect object is being moved */
  862. /*************************************************************/
  863. STDMETHODIMP CMSMFBBtn::SetObjectRects(LPCRECT prcPos,LPCRECT prcClip){
  864. // Call the default method first
  865. IOleInPlaceObjectWindowlessImpl<CMSMFBBtn>::SetObjectRects(prcPos, prcClip);
  866. return UpdateTooltipRect(prcPos);
  867. }/* end of function SetObjectRects */
  868. /*************************************************************************/
  869. /* End of file: MSMFBBtn.cpp */
  870. /*************************************************************************/