Merge XFA to PDFium master at 4dc95e7 on 10/28/2014
[pdfium.git] / xfa / src / fwl / src / basewidget / fwl_pushbuttonimp.cpp
1 // Copyright 2014 PDFium Authors. All rights reserved.\r
2 // Use of this source code is governed by a BSD-style license that can be\r
3 // found in the LICENSE file.\r
4 \r
5 // Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com\r
6 \r
7 #include "../../../foxitlib.h"\r
8 #include "../core/include/fwl_targetimp.h"\r
9 #include "../core/include/fwl_noteimp.h"\r
10 #include "../core/include/fwl_widgetimp.h"\r
11 #include "include/fwl_pushbuttonimp.h"\r
12 IFWL_PushButton *IFWL_PushButton::Create()\r
13 {\r
14     return new IFWL_PushButton;\r
15 }\r
16 FWL_ERR IFWL_PushButton::Initialize(IFWL_Widget *pOuter)\r
17 {\r
18     m_pData = FX_NEW CFWL_PushButtonImp(pOuter);\r
19     ((CFWL_PushButtonImp*)m_pData)->SetInterface(this);\r
20     return ((CFWL_PushButtonImp*)m_pData)->Initialize();\r
21 }\r
22 FWL_ERR IFWL_PushButton::Initialize(const CFWL_WidgetImpProperties &properties, IFWL_Widget *pOuter)\r
23 {\r
24     m_pData = FX_NEW CFWL_PushButtonImp(properties, pOuter);\r
25     ((CFWL_PushButtonImp*)m_pData)->SetInterface(this);\r
26     return ((CFWL_PushButtonImp*)m_pData)->Initialize();\r
27 }\r
28 IFWL_PushButton::IFWL_PushButton()\r
29 {\r
30     m_pData = NULL;\r
31 }\r
32 IFWL_PushButton::~IFWL_PushButton()\r
33 {\r
34     if (m_pData) {\r
35         delete (CFWL_PushButtonImp*)m_pData;\r
36         m_pData = NULL;\r
37     }\r
38 }\r
39 CFWL_PushButtonImp::CFWL_PushButtonImp(IFWL_Widget *pOuter )\r
40     : CFWL_WidgetImp(pOuter)\r
41     , m_bBtnDown(FALSE)\r
42     , m_dwTTOStyles(FDE_TTOSTYLE_SingleLine)\r
43     , m_iTTOAlign(FDE_TTOALIGNMENT_Center)\r
44 {\r
45     m_rtClient.Set(0, 0, 0, 0);\r
46     m_rtCaption.Set(0, 0, 0, 0);\r
47 }\r
48 CFWL_PushButtonImp::CFWL_PushButtonImp(const CFWL_WidgetImpProperties &properties, IFWL_Widget *pOuter )\r
49     : CFWL_WidgetImp(properties, pOuter)\r
50     , m_bBtnDown(FALSE)\r
51     , m_dwTTOStyles(FDE_TTOSTYLE_SingleLine)\r
52     , m_iTTOAlign(FDE_TTOALIGNMENT_Center)\r
53 {\r
54     m_rtClient.Set(0, 0, 0, 0);\r
55     m_rtCaption.Set(0, 0, 0, 0);\r
56 }\r
57 CFWL_PushButtonImp::~CFWL_PushButtonImp()\r
58 {\r
59 }\r
60 FWL_ERR CFWL_PushButtonImp::GetClassName(CFX_WideString &wsClass) const\r
61 {\r
62     wsClass = FWL_CLASS_PushButton;\r
63     return FWL_ERR_Succeeded;\r
64 }\r
65 FX_DWORD CFWL_PushButtonImp::GetClassID() const\r
66 {\r
67     return FWL_CLASSHASH_PushButton;\r
68 }\r
69 FWL_ERR CFWL_PushButtonImp::Initialize()\r
70 {\r
71     _FWL_ERR_CHECK_RETURN_VALUE_IF_FAIL(CFWL_WidgetImp::Initialize(), FWL_ERR_Indefinite);\r
72     m_pDelegate = (IFWL_WidgetDelegate*) FX_NEW CFWL_PushButtonImpDelegate(this);\r
73     return FWL_ERR_Succeeded;\r
74 }\r
75 FWL_ERR CFWL_PushButtonImp::Finalize()\r
76 {\r
77     if( m_pDelegate) {\r
78         delete (CFWL_PushButtonImpDelegate*)m_pDelegate;\r
79         m_pDelegate = NULL;\r
80     }\r
81     return CFWL_WidgetImp::Finalize();\r
82 }\r
83 FWL_ERR CFWL_PushButtonImp::GetWidgetRect(CFX_RectF &rect, FX_BOOL bAutoSize )\r
84 {\r
85     if (bAutoSize) {\r
86         rect.Set(0, 0, 0, 0);\r
87         if (m_pProperties->m_pThemeProvider == NULL) {\r
88             m_pProperties->m_pThemeProvider = GetAvailableTheme();\r
89         }\r
90         CFX_WideString wsCaption;\r
91         IFWL_PushButtonDP *pData = (IFWL_PushButtonDP*)m_pProperties->m_pDataProvider;\r
92         if (pData) {\r
93             pData->GetCaption(m_pInterface, wsCaption);\r
94         }\r
95         FX_INT32 iLen = wsCaption.GetLength();\r
96         if (iLen > 0) {\r
97             CFX_SizeF sz = CalcTextSize(wsCaption, m_pProperties->m_pThemeProvider);\r
98             rect.Set(0, 0, sz.x, sz.y);\r
99         }\r
100         FX_FLOAT *fcaption = (FX_FLOAT*)GetThemeCapacity(FWL_WGTCAPACITY_PSB_Margin);\r
101         rect.Inflate(*fcaption, *fcaption);\r
102         CFWL_WidgetImp::GetWidgetRect(rect, TRUE);\r
103     } else {\r
104         rect = m_pProperties->m_rtWidget;\r
105     }\r
106     return FWL_ERR_Succeeded;\r
107 }\r
108 FWL_ERR CFWL_PushButtonImp::SetStates(FX_DWORD dwStates, FX_BOOL bSet )\r
109 {\r
110     if ((dwStates & FWL_WGTSTATE_Disabled) && bSet) {\r
111         m_pProperties->m_dwStates = FWL_WGTSTATE_Disabled;\r
112         return FWL_ERR_Succeeded;\r
113     }\r
114     return CFWL_WidgetImp::SetStates(dwStates, bSet);\r
115 }\r
116 FWL_ERR CFWL_PushButtonImp::Update()\r
117 {\r
118     if (IsLocked()) {\r
119         return FWL_ERR_Indefinite;\r
120     }\r
121     if (!m_pProperties->m_pThemeProvider) {\r
122         m_pProperties->m_pThemeProvider = GetAvailableTheme();\r
123     }\r
124     UpdateTextOutStyles();\r
125     GetClientRect(m_rtClient);\r
126     m_rtCaption = m_rtClient;\r
127     FX_FLOAT *fcaption = (FX_FLOAT*)GetThemeCapacity(FWL_WGTCAPACITY_PSB_Margin);\r
128     m_rtCaption.Inflate(-*fcaption, -*fcaption);\r
129     return FWL_ERR_Succeeded;\r
130 }\r
131 FWL_ERR CFWL_PushButtonImp::DrawWidget(CFX_Graphics *pGraphics, const CFX_Matrix *pMatrix )\r
132 {\r
133     _FWL_RETURN_VALUE_IF_FAIL(pGraphics, FWL_ERR_Indefinite);\r
134     _FWL_RETURN_VALUE_IF_FAIL(m_pProperties->m_pThemeProvider, FWL_ERR_Indefinite);\r
135     IFWL_PushButtonDP *pData = (IFWL_PushButtonDP*)m_pProperties->m_pDataProvider;\r
136     CFX_DIBitmap *pPicture = NULL;\r
137     IFWL_ThemeProvider *pTheme = m_pProperties->m_pThemeProvider;\r
138     if (HasBorder()) {\r
139         DrawBorder(pGraphics, FWL_PART_PSB_Border, m_pProperties->m_pThemeProvider, pMatrix);\r
140     }\r
141     if (HasEdge()) {\r
142         DrawEdge(pGraphics, FWL_PART_PSB_Edge, m_pProperties->m_pThemeProvider, pMatrix);\r
143     }\r
144     DrawBkground(pGraphics, m_pProperties->m_pThemeProvider, pMatrix);\r
145     CFX_Matrix matrix;\r
146     matrix.Concat(*pMatrix);\r
147     FX_FLOAT iPicwidth = 0;\r
148     FX_FLOAT ipicheight = 0;\r
149     CFX_WideString wsCaption;\r
150     if (pData) {\r
151         pData->GetCaption(m_pInterface, wsCaption);\r
152     }\r
153     CFX_RectF rtText;\r
154     rtText.Set(0, 0, 0 , 0);\r
155     if (!wsCaption.IsEmpty()) {\r
156         CalcTextRect(wsCaption, pTheme, 0, m_iTTOAlign, rtText);\r
157     }\r
158     switch(m_pProperties->m_dwStyleExes & FWL_STYLEEXT_PSB_ModeMask) {\r
159         case FWL_STYLEEXT_PSB_TextOnly:\r
160             DrawText(pGraphics, m_pProperties->m_pThemeProvider, &matrix);\r
161             break;\r
162         case FWL_STYLEEXT_PSB_IconOnly:\r
163             if (pData) {\r
164                 pPicture = pData->GetPicture(m_pInterface);\r
165             }\r
166             if (pPicture) {\r
167                 CFX_PointF point;\r
168                 switch(m_iTTOAlign) {\r
169                     case 0: {\r
170                             point.x = m_rtClient.left;\r
171                             point.y =  m_rtClient.top;\r
172                             break;\r
173                         }\r
174                     case 1: {\r
175                             point.x = m_rtClient.left + (m_rtClient.width / 2 - pPicture->GetWidth() / 2);\r
176                             point.y =  m_rtClient.top;\r
177                             break;\r
178                         }\r
179                     case 2:\r
180                         point.x = m_rtClient.left + m_rtClient.width - pPicture->GetWidth();\r
181                         point.y = m_rtClient.top;\r
182                         break;\r
183                     case 4:\r
184                         point.x = m_rtClient.left;\r
185                         point.y = m_rtClient.top + m_rtClient.height / 2 - pPicture->GetHeight() / 2;\r
186                         break;\r
187                     case 5:\r
188                         point.x = m_rtClient.left + (m_rtClient.width / 2 - pPicture->GetWidth() / 2);\r
189                         point.y =  m_rtClient.top + m_rtClient.height / 2 - pPicture->GetHeight() / 2;\r
190                         break;\r
191                     case 6:\r
192                         point.x = m_rtClient.left + m_rtClient.width - pPicture->GetWidth();\r
193                         point.y = m_rtClient.top  + m_rtClient.height / 2 - pPicture->GetHeight() / 2;\r
194                         break;\r
195                     case 8:\r
196                         point.x = m_rtClient.left;\r
197                         point.y =  m_rtClient.top + m_rtClient.height - pPicture->GetHeight();\r
198                         break;\r
199                     case 9:\r
200                         point.x = m_rtClient.left + (m_rtClient.width / 2 - pPicture->GetWidth() / 2);\r
201                         point.y =  m_rtClient.top + m_rtClient.height - pPicture->GetHeight();\r
202                         break;\r
203                     case 10:\r
204                         point.x = m_rtClient.left + m_rtClient.width - pPicture->GetWidth();\r
205                         point.y = m_rtClient.top  + m_rtClient.height - pPicture->GetHeight();\r
206                         break;\r
207                 }\r
208                 pGraphics->DrawImage(pPicture, point, &matrix);\r
209             }\r
210             break;\r
211         case FWL_STYLEEXT_PSB_TextIcon:\r
212             if (pPicture) {\r
213                 CFX_PointF point;\r
214                 switch(m_iTTOAlign) {\r
215                     case 0: {\r
216                             point.x = m_rtClient.left;\r
217                             point.y =  m_rtClient.top;\r
218                             iPicwidth = (FX_FLOAT)(pPicture->GetWidth() - 7);\r
219                             ipicheight = pPicture->GetHeight() / 2 - m_rtCaption.top - rtText.height / 2;\r
220                             break;\r
221                         }\r
222                     case 1: {\r
223                             point.x = m_rtClient.left + (m_rtClient.width / 2 - (pPicture->GetWidth() + rtText.width) / 2);\r
224                             point.y =  m_rtClient.top;\r
225                             iPicwidth = pPicture->GetWidth() - ((m_rtClient.width) / 2 - rtText.width / 2 - point.x) + rtText.width / 2 - 7;\r
226                             ipicheight = pPicture->GetHeight() / 2 - m_rtCaption.top - rtText.height / 2;\r
227                             break;\r
228                         }\r
229                     case 2:\r
230                         point.x = m_rtClient.left + m_rtClient.width - pPicture->GetWidth() - rtText.width;\r
231                         point.y = m_rtClient.top;\r
232                         iPicwidth =  m_rtClient.left + m_rtClient.width - point.x - pPicture->GetWidth() - rtText.width + 7;\r
233                         ipicheight = pPicture->GetHeight() / 2 - m_rtCaption.top - rtText.height / 2;\r
234                         break;\r
235                     case 4:\r
236                         point.x = m_rtClient.left;\r
237                         point.y = m_rtClient.top + m_rtClient.height / 2 - pPicture->GetHeight() / 2;\r
238                         iPicwidth = m_rtClient.left + pPicture->GetWidth() - 7;\r
239                         break;\r
240                     case 5:\r
241                         point.x = m_rtClient.left + (m_rtClient.width / 2 - (pPicture->GetWidth() + rtText.width) / 2);\r
242                         point.y =  m_rtClient.top + m_rtClient.height / 2 - pPicture->GetHeight() / 2;\r
243                         iPicwidth = pPicture->GetWidth() - ((m_rtClient.width) / 2 - rtText.width / 2 - point.x) + rtText.width / 2 - 7;\r
244                         break;\r
245                     case 6:\r
246                         point.x = m_rtClient.left + m_rtClient.width - pPicture->GetWidth() - rtText.width;\r
247                         point.y = m_rtClient.top  + m_rtClient.height / 2 - pPicture->GetHeight() / 2;\r
248                         iPicwidth =  m_rtClient.left + m_rtClient.width - point.x - pPicture->GetWidth() - rtText.width + 7;\r
249                         break;\r
250                     case 8:\r
251                         point.x = m_rtClient.left;\r
252                         point.y =  m_rtClient.top + m_rtClient.height - pPicture->GetHeight();\r
253                         iPicwidth = (FX_FLOAT)(pPicture->GetWidth() - 7);\r
254                         ipicheight -= rtText.height / 2;\r
255                         break;\r
256                     case 9:\r
257                         point.x = m_rtClient.left + (m_rtClient.width / 2 - (pPicture->GetWidth() + rtText.width) / 2);\r
258                         point.y =  m_rtClient.top + m_rtClient.height - pPicture->GetHeight();\r
259                         iPicwidth = pPicture->GetWidth() - ((m_rtClient.width) / 2 - rtText.width / 2 - point.x) + rtText.width / 2 - 7;\r
260                         ipicheight -= rtText.height / 2;\r
261                         break;\r
262                     case 10:\r
263                         point.x = m_rtClient.left + m_rtClient.width - pPicture->GetWidth() - rtText.width;\r
264                         point.y = m_rtClient.top  + m_rtClient.height - pPicture->GetHeight();\r
265                         iPicwidth =  m_rtClient.left + m_rtClient.width - point.x - pPicture->GetWidth() - rtText.width + 7;\r
266                         ipicheight -= rtText.height / 2;\r
267                         break;\r
268                 }\r
269                 pGraphics->DrawImage(pPicture, point, &matrix);\r
270             }\r
271             matrix.e += m_rtClient.left + iPicwidth;\r
272             matrix.f += m_rtClient.top + ipicheight;\r
273             DrawText(pGraphics, m_pProperties->m_pThemeProvider, &matrix);\r
274             break;\r
275     }\r
276     return FWL_ERR_Succeeded;\r
277 }\r
278 void CFWL_PushButtonImp::DrawBkground(CFX_Graphics *pGraphics, IFWL_ThemeProvider *pTheme, const CFX_Matrix *pMatrix)\r
279 {\r
280     CFWL_ThemeBackground param;\r
281     param.m_pWidget = m_pInterface;\r
282     param.m_iPart = FWL_PART_PSB_Background;\r
283     param.m_dwStates = GetPartStates();\r
284     param.m_pGraphics = pGraphics;\r
285     if (pMatrix) {\r
286         param.m_matrix.Concat(*pMatrix);\r
287     }\r
288     param.m_rtPart = m_rtClient;\r
289     if (m_pProperties->m_dwStates & FWL_WGTSTATE_Focused) {\r
290         param.m_pData = &m_rtCaption;\r
291     }\r
292     pTheme->DrawBackground(&param);\r
293 }\r
294 void CFWL_PushButtonImp::DrawText(CFX_Graphics *pGraphics, IFWL_ThemeProvider *pTheme, const CFX_Matrix *pMatrix)\r
295 {\r
296     _FWL_RETURN_IF_FAIL(m_pProperties->m_pDataProvider);\r
297     CFX_WideString wsCaption;\r
298     m_pProperties->m_pDataProvider->GetCaption(m_pInterface, wsCaption);\r
299     if (wsCaption.IsEmpty()) {\r
300         return;\r
301     }\r
302     CFWL_ThemeText param;\r
303     param.m_pWidget = m_pInterface;\r
304     param.m_iPart = FWL_PART_PSB_Caption;\r
305     param.m_dwStates = GetPartStates();\r
306     param.m_pGraphics = pGraphics;\r
307     if (pMatrix) {\r
308         param.m_matrix.Concat(*pMatrix);\r
309     }\r
310     param.m_rtPart = m_rtCaption;\r
311     param.m_wsText = wsCaption;\r
312     param.m_dwTTOStyles = m_dwTTOStyles;\r
313     param.m_iTTOAlign = m_iTTOAlign;\r
314     pTheme->DrawText(&param);\r
315 }\r
316 FX_DWORD CFWL_PushButtonImp::GetPartStates()\r
317 {\r
318     FX_DWORD dwStates = FWL_PARTSTATE_PSB_Normal;\r
319     if (m_pProperties->m_dwStates & FWL_WGTSTATE_Focused) {\r
320         dwStates |= FWL_PARTSTATE_PSB_Focused;\r
321     }\r
322     if (m_pProperties->m_dwStates & FWL_WGTSTATE_Disabled) {\r
323         dwStates = FWL_PARTSTATE_PSB_Disabled;\r
324     } else if (m_pProperties->m_dwStates & FWL_STATE_PSB_Pressed) {\r
325         dwStates |= FWL_PARTSTATE_PSB_Pressed;\r
326     } else if (m_pProperties->m_dwStates & FWL_STATE_PSB_Hovered) {\r
327         dwStates |= FWL_PARTSTATE_PSB_Hovered;\r
328     } else if (m_pProperties->m_dwStates & FWL_STATE_PSB_Default) {\r
329         dwStates |= FWL_PARTSTATE_PSB_Default;\r
330     }\r
331     return dwStates;\r
332 }\r
333 void CFWL_PushButtonImp::UpdateTextOutStyles()\r
334 {\r
335     m_iTTOAlign = FDE_TTOALIGNMENT_Center;\r
336     switch(m_pProperties->m_dwStyleExes & (FWL_STYLEEXT_PSB_HLayoutMask | FWL_STYLEEXT_PSB_VLayoutMask)) {\r
337         case FWL_STYLEEXT_PSB_Left | FWL_STYLEEXT_PSB_Top: {\r
338                 m_iTTOAlign = FDE_TTOALIGNMENT_TopLeft;\r
339                 break;\r
340             }\r
341         case FWL_STYLEEXT_PSB_Center | FWL_STYLEEXT_PSB_Top: {\r
342                 m_iTTOAlign = FDE_TTOALIGNMENT_TopCenter;\r
343                 break;\r
344             }\r
345         case FWL_STYLEEXT_PSB_Right | FWL_STYLEEXT_PSB_Top: {\r
346                 m_iTTOAlign = FDE_TTOALIGNMENT_TopRight;\r
347                 break;\r
348             }\r
349         case FWL_STYLEEXT_PSB_Left | FWL_STYLEEXT_PSB_VCenter: {\r
350                 m_iTTOAlign = FDE_TTOALIGNMENT_CenterLeft;\r
351                 break;\r
352             }\r
353         case FWL_STYLEEXT_PSB_Center | FWL_STYLEEXT_PSB_VCenter: {\r
354                 m_iTTOAlign = FDE_TTOALIGNMENT_Center;\r
355                 break;\r
356             }\r
357         case FWL_STYLEEXT_PSB_Right | FWL_STYLEEXT_PSB_VCenter: {\r
358                 m_iTTOAlign = FDE_TTOALIGNMENT_CenterRight;\r
359                 break;\r
360             }\r
361         case FWL_STYLEEXT_PSB_Left | FWL_STYLEEXT_PSB_Bottom: {\r
362                 m_iTTOAlign = FDE_TTOALIGNMENT_BottomLeft;\r
363                 break;\r
364             }\r
365         case FWL_STYLEEXT_PSB_Center | FWL_STYLEEXT_PSB_Bottom: {\r
366                 m_iTTOAlign = FDE_TTOALIGNMENT_BottomCenter;\r
367                 break;\r
368             }\r
369         case FWL_STYLEEXT_PSB_Right | FWL_STYLEEXT_PSB_Bottom: {\r
370                 m_iTTOAlign = FDE_TTOALIGNMENT_BottomRight;\r
371                 break;\r
372             }\r
373         default: {\r
374             }\r
375     }\r
376     m_dwTTOStyles = FDE_TTOSTYLE_SingleLine;\r
377     if (m_pProperties->m_dwStyleExes & FWL_WGTSTYLE_RTLReading) {\r
378         m_dwTTOStyles |= FDE_TTOSTYLE_RTL;\r
379     }\r
380 }\r
381 CFWL_PushButtonImpDelegate::CFWL_PushButtonImpDelegate(CFWL_PushButtonImp *pOwner)\r
382     : m_pOwner(pOwner)\r
383 {\r
384 }\r
385 FX_INT32 CFWL_PushButtonImpDelegate::OnProcessMessage(CFWL_Message *pMessage)\r
386 {\r
387     _FWL_RETURN_VALUE_IF_FAIL(pMessage, 0);\r
388     if (!m_pOwner->IsEnabled()) {\r
389         return 1;\r
390     }\r
391     FX_INT32 iRet = 1;\r
392     FX_DWORD dwMsgCode = pMessage->GetClassID();\r
393     switch (dwMsgCode) {\r
394         case FWL_MSGHASH_SetFocus:\r
395         case FWL_MSGHASH_KillFocus: {\r
396                 OnFocusChanged(pMessage, dwMsgCode == FWL_MSGHASH_SetFocus);\r
397                 break;\r
398             }\r
399         case FWL_MSGHASH_Mouse: {\r
400                 CFWL_MsgMouse *pMsg = (CFWL_MsgMouse*)pMessage;\r
401                 FX_DWORD dwCmd = pMsg->m_dwCmd;\r
402                 switch (dwCmd) {\r
403                     case FWL_MSGMOUSECMD_LButtonDown: {\r
404                             OnLButtonDown(pMsg);\r
405                             break;\r
406                         }\r
407                     case FWL_MSGMOUSECMD_LButtonUp: {\r
408                             OnLButtonUp(pMsg);\r
409                             break;\r
410                         }\r
411                     case FWL_MSGMOUSECMD_MouseMove: {\r
412                             OnMouseMove(pMsg);\r
413                             break;\r
414                         }\r
415                     case FWL_MSGMOUSECMD_MouseLeave: {\r
416                             OnMouseLeave(pMsg);\r
417                             break;\r
418                         }\r
419                     default: {\r
420                         }\r
421                 }\r
422                 break;\r
423             }\r
424         case FWL_MSGHASH_Key: {\r
425                 CFWL_MsgKey *pKey = (CFWL_MsgKey*)pMessage;\r
426                 if (pKey->m_dwCmd == FWL_MSGKEYCMD_KeyDown) {\r
427                     OnKeyDown((CFWL_MsgKey*)pKey);\r
428                 }\r
429                 break;\r
430             }\r
431         default: {\r
432                 iRet = 0;\r
433                 break;\r
434             }\r
435     }\r
436     CFWL_WidgetImpDelegate::OnProcessMessage(pMessage);\r
437     return iRet;\r
438 }\r
439 FWL_ERR CFWL_PushButtonImpDelegate::OnProcessEvent(CFWL_Event *pEvent)\r
440 {\r
441     return FWL_ERR_Succeeded;\r
442 }\r
443 FWL_ERR CFWL_PushButtonImpDelegate::OnDrawWidget(CFX_Graphics *pGraphics, const CFX_Matrix *pMatrix )\r
444 {\r
445     return m_pOwner->DrawWidget(pGraphics, pMatrix);\r
446 }\r
447 void CFWL_PushButtonImpDelegate::OnFocusChanged(CFWL_Message *pMsg, FX_BOOL bSet )\r
448 {\r
449     if (bSet) {\r
450         m_pOwner->m_pProperties->m_dwStates |= FWL_WGTSTATE_Focused;\r
451     } else {\r
452         m_pOwner->m_pProperties->m_dwStates &= ~FWL_WGTSTATE_Focused;\r
453     }\r
454     m_pOwner->Repaint(&m_pOwner->m_rtClient);\r
455 }\r
456 void CFWL_PushButtonImpDelegate::OnLButtonDown(CFWL_MsgMouse *pMsg)\r
457 {\r
458     if ((m_pOwner->m_pProperties->m_dwStates & FWL_WGTSTATE_Focused) == 0) {\r
459         m_pOwner->SetFocus(TRUE);\r
460     }\r
461     m_pOwner->m_bBtnDown = TRUE;\r
462     m_pOwner->m_pProperties->m_dwStates |= FWL_STATE_PSB_Hovered;\r
463     m_pOwner->m_pProperties->m_dwStates |= FWL_STATE_PSB_Pressed;\r
464     m_pOwner->Repaint(&m_pOwner->m_rtClient);\r
465 }\r
466 void CFWL_PushButtonImpDelegate::OnLButtonUp(CFWL_MsgMouse *pMsg)\r
467 {\r
468     m_pOwner->m_bBtnDown = FALSE;\r
469     if (m_pOwner->m_rtClient.Contains(pMsg->m_fx, pMsg->m_fy)) {\r
470         m_pOwner->m_pProperties->m_dwStates &= ~FWL_STATE_PSB_Pressed;\r
471         m_pOwner->m_pProperties->m_dwStates |= FWL_STATE_PSB_Hovered;\r
472     } else {\r
473         m_pOwner->m_pProperties->m_dwStates &= ~FWL_STATE_PSB_Hovered;\r
474         m_pOwner->m_pProperties->m_dwStates &= ~FWL_STATE_PSB_Pressed;\r
475     }\r
476     if (m_pOwner->m_rtClient.Contains(pMsg->m_fx, pMsg->m_fy)) {\r
477         CFWL_EvtClick wmClick;\r
478         wmClick.m_pSrcTarget = (IFWL_PushButton*)m_pOwner->m_pInterface;\r
479         m_pOwner->DispatchEvent(&wmClick);\r
480     }\r
481     m_pOwner->Repaint(&m_pOwner->m_rtClient);\r
482 }\r
483 void CFWL_PushButtonImpDelegate::OnMouseMove(CFWL_MsgMouse *pMsg)\r
484 {\r
485     FX_BOOL bRepaint = FALSE;\r
486     if (m_pOwner->m_bBtnDown) {\r
487         if (m_pOwner->m_rtClient.Contains(pMsg->m_fx, pMsg->m_fy)) {\r
488             if ((m_pOwner->m_pProperties->m_dwStates & FWL_STATE_PSB_Pressed) == 0) {\r
489                 m_pOwner->m_pProperties->m_dwStates |= FWL_STATE_PSB_Pressed;\r
490                 bRepaint = TRUE;\r
491             }\r
492             if (m_pOwner->m_pProperties->m_dwStates & FWL_STATE_PSB_Hovered) {\r
493                 m_pOwner->m_pProperties->m_dwStates &= ~FWL_STATE_PSB_Hovered;\r
494                 bRepaint = TRUE;\r
495             }\r
496         } else {\r
497             if (m_pOwner->m_pProperties->m_dwStates & FWL_STATE_PSB_Pressed) {\r
498                 m_pOwner->m_pProperties->m_dwStates &= ~FWL_STATE_PSB_Pressed;\r
499                 bRepaint = TRUE;\r
500             }\r
501             if ((m_pOwner->m_pProperties->m_dwStates & FWL_STATE_PSB_Hovered) == 0) {\r
502                 m_pOwner->m_pProperties->m_dwStates |= FWL_STATE_PSB_Hovered;\r
503                 bRepaint = TRUE;\r
504             }\r
505         }\r
506     } else {\r
507         if (!m_pOwner->m_rtClient.Contains(pMsg->m_fx, pMsg->m_fy)) {\r
508             return;\r
509         }\r
510         if ((m_pOwner->m_pProperties->m_dwStates & FWL_STATE_PSB_Hovered) == 0) {\r
511             m_pOwner->m_pProperties->m_dwStates |= FWL_STATE_PSB_Hovered;\r
512             bRepaint = TRUE;\r
513         }\r
514     }\r
515     if (bRepaint) {\r
516         m_pOwner->Repaint(&m_pOwner->m_rtClient);\r
517     }\r
518 }\r
519 void CFWL_PushButtonImpDelegate::OnMouseLeave(CFWL_MsgMouse *pMsg)\r
520 {\r
521     m_pOwner->m_bBtnDown = FALSE;\r
522     m_pOwner->m_pProperties->m_dwStates &= ~FWL_STATE_PSB_Hovered;\r
523     m_pOwner->m_pProperties->m_dwStates &= ~FWL_STATE_PSB_Pressed;\r
524     m_pOwner->Repaint(&m_pOwner->m_rtClient);\r
525 }\r
526 void CFWL_PushButtonImpDelegate::OnKeyDown(CFWL_MsgKey *pMsg)\r
527 {\r
528     if (pMsg->m_dwKeyCode == FWL_VKEY_Return) {\r
529         CFWL_EvtMouse wmMouse;\r
530         wmMouse.m_pSrcTarget = m_pOwner->m_pInterface;\r
531         wmMouse.m_dwCmd = FWL_MSGMOUSECMD_LButtonUp;\r
532         m_pOwner->DispatchEvent(&wmMouse);\r
533         CFWL_EvtClick wmClick;\r
534         wmClick.m_pSrcTarget = (IFWL_PushButton*)m_pOwner->m_pInterface;\r
535         m_pOwner->DispatchEvent(&wmClick);\r
536         return;\r
537     }\r
538     if (pMsg->m_dwKeyCode != FWL_VKEY_Tab) {\r
539         return;\r
540     }\r
541     m_pOwner->DispatchKeyEvent(pMsg);\r
542 }\r