Merge XFA to PDFium master at 4dc95e7 on 10/28/2014
[pdfium.git] / xfa / src / fxfa / src / app / xfa_ffwidgetacc.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 "../common/xfa_common.h"\r
9 #include "xfa_ffwidget.h"\r
10 #include "xfa_ffdoc.h"\r
11 #include "xfa_ffdocview.h"\r
12 #include "xfa_ffpageview.h"\r
13 #include "xfa_ffapp.h"\r
14 #include "xfa_textlayout.h"\r
15 #include "xfa_fwladapter.h"\r
16 #include "xfa_fffield.h"\r
17 #include "xfa_ffchoicelist.h"\r
18 #include "xfa_ffcheckbutton.h"\r
19 #include "xfa_ffwidgetacc.h"\r
20 #include "xfa_fontmgr.h"\r
21 static void XFA_FFDeleteCalcData(FX_LPVOID pData)\r
22 {\r
23     if (pData) {\r
24         delete ((CXFA_CalcData*)pData);\r
25     }\r
26 }\r
27 static XFA_MAPDATABLOCKCALLBACKINFO gs_XFADeleteCalcData = {XFA_FFDeleteCalcData, NULL};\r
28 class CXFA_WidgetLayoutData : public CFX_Object\r
29 {\r
30 public:\r
31     CXFA_WidgetLayoutData()\r
32         : m_fWidgetHeight(-1)\r
33     {\r
34     }\r
35     virtual ~CXFA_WidgetLayoutData() {}\r
36     virtual void Release()\r
37     {\r
38         delete this;\r
39     }\r
40     FX_FLOAT                    m_fWidgetHeight;\r
41 };\r
42 class CXFA_TextLayoutData : public CXFA_WidgetLayoutData\r
43 {\r
44 public:\r
45     CXFA_TextLayoutData()\r
46         : m_pTextLayout(NULL)\r
47         , m_pTextProvider(NULL)\r
48     {\r
49     }\r
50     ~CXFA_TextLayoutData()\r
51     {\r
52         if (m_pTextLayout) {\r
53             delete m_pTextLayout;\r
54         }\r
55         m_pTextLayout = NULL;\r
56         if (m_pTextProvider) {\r
57             delete m_pTextProvider;\r
58         }\r
59         m_pTextProvider = NULL;\r
60     }\r
61     FX_BOOL LoadText(CXFA_WidgetAcc* pAcc)\r
62     {\r
63         if (m_pTextLayout) {\r
64             return TRUE;\r
65         }\r
66         m_pTextProvider = FX_NEW CXFA_TextProvider(pAcc, XFA_TEXTPROVIDERTYPE_Text);\r
67         m_pTextLayout = FX_NEW CXFA_TextLayout(m_pTextProvider);\r
68         return m_pTextLayout != NULL;\r
69     }\r
70     CXFA_TextLayout*    m_pTextLayout;\r
71     CXFA_TextProvider   *m_pTextProvider;\r
72 };\r
73 class CXFA_ImageLayoutData : public CXFA_WidgetLayoutData\r
74 {\r
75 public:\r
76     CXFA_ImageLayoutData()\r
77         : m_pDIBitmap(NULL)\r
78         , m_bNamedImage(FALSE)\r
79         , m_iImageXDpi(0)\r
80         , m_iImageYDpi(0)\r
81     {\r
82     }\r
83 \r
84     ~CXFA_ImageLayoutData()\r
85     {\r
86         if(m_pDIBitmap && !m_bNamedImage) {\r
87             delete m_pDIBitmap;\r
88         }\r
89         m_pDIBitmap = NULL;\r
90     }\r
91 \r
92     FX_BOOL LoadImageData(CXFA_WidgetAcc* pAcc)\r
93     {\r
94         if(m_pDIBitmap) {\r
95             return TRUE;\r
96         }\r
97         CXFA_Value value = pAcc->GetFormValue();\r
98         if (!value) {\r
99             return FALSE;\r
100         }\r
101         CXFA_Image imageObj = value.GetImage();\r
102         if (!imageObj) {\r
103             return FALSE;\r
104         }\r
105         CXFA_FFDoc *pFFDoc = pAcc->GetDoc();\r
106         pAcc->SetImageImage(XFA_LoadImageData(pFFDoc, &imageObj, m_bNamedImage, m_iImageXDpi, m_iImageYDpi));\r
107         return m_pDIBitmap != NULL;\r
108     }\r
109 \r
110     CFX_DIBitmap*                       m_pDIBitmap;\r
111     FX_BOOL                                     m_bNamedImage;\r
112     FX_INT32                            m_iImageXDpi;\r
113     FX_INT32                            m_iImageYDpi;\r
114 };\r
115 class CXFA_FieldLayoutData : public CXFA_WidgetLayoutData\r
116 {\r
117 public:\r
118     CXFA_FieldLayoutData()\r
119         : m_pCapTextLayout(NULL)\r
120         , m_pCapTextProvider(NULL)\r
121         , m_pTextOut(NULL)\r
122         , m_pFieldSplitArray(NULL)\r
123     {\r
124     }\r
125     ~CXFA_FieldLayoutData()\r
126     {\r
127         if (m_pCapTextLayout) {\r
128             delete m_pCapTextLayout;\r
129         }\r
130         m_pCapTextLayout = NULL;\r
131         if (m_pCapTextProvider) {\r
132             delete m_pCapTextProvider;\r
133         }\r
134         m_pCapTextProvider = NULL;\r
135         if (m_pTextOut) {\r
136             m_pTextOut->Release();\r
137         }\r
138         m_pTextOut = NULL;\r
139         if (m_pFieldSplitArray) {\r
140             m_pFieldSplitArray->RemoveAll();\r
141             delete m_pFieldSplitArray;\r
142             m_pFieldSplitArray = NULL;\r
143         }\r
144     }\r
145     FX_BOOL LoadCaption(CXFA_WidgetAcc* pAcc)\r
146     {\r
147         if (m_pCapTextLayout) {\r
148             return TRUE;\r
149         }\r
150         CXFA_Caption caption = pAcc->GetCaption();\r
151         if (caption.IsExistInXML() && caption.GetPresence() != XFA_ATTRIBUTEENUM_Hidden) {\r
152             m_pCapTextProvider = FX_NEW CXFA_TextProvider(pAcc, XFA_TEXTPROVIDERTYPE_Caption);\r
153             m_pCapTextLayout = FX_NEW CXFA_TextLayout(m_pCapTextProvider);\r
154             return m_pCapTextLayout != NULL;\r
155         }\r
156         return FALSE;\r
157     }\r
158     CXFA_TextLayout             *m_pCapTextLayout;\r
159     CXFA_TextProvider   *m_pCapTextProvider;\r
160     IFDE_TextOut                *m_pTextOut;\r
161     CFX_FloatArray              *m_pFieldSplitArray;\r
162 };\r
163 class CXFA_TextEditData : public CXFA_FieldLayoutData\r
164 {\r
165 public:\r
166 };\r
167 class CXFA_ImageEditData : public CXFA_FieldLayoutData\r
168 {\r
169 public:\r
170     CXFA_ImageEditData()\r
171         : m_pDIBitmap(NULL)\r
172         , m_bNamedImage(FALSE)\r
173         , m_iImageXDpi(0)\r
174         , m_iImageYDpi(0)\r
175     {\r
176     }\r
177 \r
178     ~CXFA_ImageEditData()\r
179     {\r
180         if(m_pDIBitmap && !m_bNamedImage) {\r
181             delete m_pDIBitmap;\r
182         }\r
183         m_pDIBitmap = NULL;\r
184     }\r
185     FX_BOOL LoadImageData(CXFA_WidgetAcc* pAcc)\r
186     {\r
187         if(m_pDIBitmap) {\r
188             return TRUE;\r
189         }\r
190         CXFA_Value value = pAcc->GetFormValue();\r
191         if (!value) {\r
192             return FALSE;\r
193         }\r
194         CXFA_Image imageObj = value.GetImage();\r
195         CXFA_FFDoc *pFFDoc = pAcc->GetDoc();\r
196         pAcc->SetImageEditImage(XFA_LoadImageData(pFFDoc, &imageObj, m_bNamedImage, m_iImageXDpi, m_iImageYDpi));\r
197         return m_pDIBitmap != NULL;\r
198     }\r
199     CFX_DIBitmap*                       m_pDIBitmap;\r
200     FX_BOOL                                     m_bNamedImage;\r
201     FX_INT32                            m_iImageXDpi;\r
202     FX_INT32                            m_iImageYDpi;\r
203 };\r
204 CXFA_WidgetAcc::CXFA_WidgetAcc(CXFA_FFDocView* pDocView, CXFA_Node* pNode)\r
205     : CXFA_WidgetData(pNode)\r
206     , m_pDocView(pDocView)\r
207     , m_pLayoutData(NULL)\r
208 {\r
209 }\r
210 CXFA_WidgetAcc::~CXFA_WidgetAcc()\r
211 {\r
212     if (m_pLayoutData) {\r
213         m_pLayoutData->Release();\r
214         m_pLayoutData = NULL;\r
215     }\r
216 }\r
217 FX_BOOL CXFA_WidgetAcc::GetName(CFX_WideString &wsName, FX_INT32 iNameType )\r
218 {\r
219     if (iNameType == 0) {\r
220         m_pNode->TryCData(XFA_ATTRIBUTE_Name, wsName);\r
221         return !wsName.IsEmpty();\r
222     }\r
223     m_pNode->GetSOMExpression(wsName);\r
224     if (iNameType == 2 && wsName.GetLength() >= 15) {\r
225         CFX_WideStringC wsPre = FX_WSTRC(L"xfa[0].form[0].");\r
226         if (wsPre == CFX_WideStringC(wsName, wsPre.GetLength())) {\r
227             wsName.Delete(0, wsPre.GetLength());\r
228         }\r
229     }\r
230     return TRUE;\r
231 }\r
232 CXFA_Node* CXFA_WidgetAcc::GetDatasets()\r
233 {\r
234     return m_pNode->GetBindData();\r
235 }\r
236 FX_BOOL CXFA_WidgetAcc::ProcessValueChanged()\r
237 {\r
238     m_pDocView->AddValidateWidget(this);\r
239     m_pDocView->AddCalculateWidgetAcc(this);\r
240     m_pDocView->RunCalculateWidgets();\r
241     m_pDocView->RunValidate();\r
242     return TRUE;\r
243 }\r
244 void CXFA_WidgetAcc::ResetData()\r
245 {\r
246     CFX_WideString wsValue;\r
247     XFA_ELEMENT eUIType = (XFA_ELEMENT)GetUIType();\r
248     switch (eUIType) {\r
249         case XFA_ELEMENT_ImageEdit: {\r
250                 CXFA_Value imageValue = GetDefaultValue();\r
251                 CXFA_Image image = imageValue.GetImage();\r
252                 CFX_WideString wsContentType, wsHref;\r
253                 if (image) {\r
254                     image.GetContent(wsValue);\r
255                     image.GetContentType(wsContentType);\r
256                     image.GetHref(wsHref);\r
257                 }\r
258                 SetImageEdit(wsContentType, wsHref, wsValue);\r
259             }\r
260             break;\r
261         case XFA_ELEMENT_ExclGroup: {\r
262                 CXFA_Node* pNextChild = m_pNode->GetNodeItem(XFA_NODEITEM_FirstChild, XFA_OBJECTTYPE_ContainerNode);\r
263                 while (pNextChild) {\r
264                     CXFA_Node* pChild = pNextChild;\r
265                     CXFA_WidgetAcc* pAcc = (CXFA_WidgetAcc*)pChild->GetWidgetData();\r
266                     if (!pAcc) {\r
267                         continue;\r
268                     }\r
269                     CXFA_Value defValue(NULL);\r
270                     if (wsValue.IsEmpty() && (defValue = pAcc->GetDefaultValue())) {\r
271                         defValue.GetChildValueContent(wsValue);\r
272                         this->SetValue(wsValue, XFA_VALUEPICTURE_Raw);\r
273                         pAcc->SetValue(wsValue, XFA_VALUEPICTURE_Raw);\r
274                     } else {\r
275                         CXFA_Node* pItems = pChild->GetChild(0, XFA_ELEMENT_Items);\r
276                         if (!pItems) {\r
277                             continue;\r
278                         }\r
279                         CFX_WideString itemText;\r
280                         if (pItems->CountChildren(XFA_ELEMENT_UNKNOWN) > 1) {\r
281                             itemText = pItems->GetChild(1, XFA_ELEMENT_UNKNOWN)->GetContent();\r
282                         }\r
283                         pAcc->SetValue(itemText, XFA_VALUEPICTURE_Raw);\r
284                     }\r
285                     pNextChild = pChild->GetNodeItem(XFA_NODEITEM_NextSibling, XFA_OBJECTTYPE_ContainerNode);\r
286                 }\r
287             }\r
288             break;\r
289         case XFA_ELEMENT_ChoiceList:\r
290             ClearAllSelections();\r
291         default:\r
292             if (CXFA_Value defValue = GetDefaultValue()) {\r
293                 defValue.GetChildValueContent(wsValue);\r
294             }\r
295             SetValue(wsValue, XFA_VALUEPICTURE_Raw);\r
296             break;\r
297     }\r
298 }\r
299 void CXFA_WidgetAcc::SetImageEdit(FX_WSTR wsContentType, FX_WSTR wsHref, FX_WSTR wsData)\r
300 {\r
301     CXFA_Image image = GetFormValue().GetImage();\r
302     if (image) {\r
303         image.SetContentType(wsContentType);\r
304         image.SetHref(wsHref);\r
305     }\r
306     CFX_WideString wsFormatValue(wsData);\r
307     this->GetFormatDataValue(wsData, wsFormatValue);\r
308     m_pNode->SetContent(wsData, wsFormatValue, TRUE);\r
309     CXFA_Node* pBind = GetDatasets();\r
310     if (!pBind) {\r
311         image.SetTransferEncoding(XFA_ATTRIBUTEENUM_Base64);\r
312         return;\r
313     }\r
314     pBind->SetCData(XFA_ATTRIBUTE_ContentType, wsContentType);\r
315     CXFA_Node *pHrefNode = pBind->GetNodeItem(XFA_NODEITEM_FirstChild);\r
316     if (pHrefNode) {\r
317         pHrefNode->SetCData(XFA_ATTRIBUTE_Value, wsHref);\r
318     } else {\r
319         IFDE_XMLNode *pXMLNode = pBind->GetXMLMappingNode();\r
320         FXSYS_assert(pXMLNode && pXMLNode->GetType() == FDE_XMLNODE_Element);\r
321         ((IFDE_XMLElement*)pXMLNode)->SetString(FX_WSTRC(L"href"), wsHref);\r
322     }\r
323 }\r
324 \r
325 CXFA_WidgetAcc* CXFA_WidgetAcc::GetExclGroup()\r
326 {\r
327     CXFA_Node* pExcl = m_pNode->GetNodeItem(XFA_NODEITEM_Parent);\r
328     if (!pExcl || pExcl->GetClassID() != XFA_ELEMENT_ExclGroup) {\r
329         return NULL;\r
330     }\r
331     return (CXFA_WidgetAcc*)pExcl->GetWidgetData();\r
332 }\r
333 CXFA_FFDocView* CXFA_WidgetAcc::GetDocView()\r
334 {\r
335     return m_pDocView;\r
336 }\r
337 CXFA_FFDoc* CXFA_WidgetAcc::GetDoc()\r
338 {\r
339     return (CXFA_FFDoc*)m_pDocView->GetDoc();\r
340 }\r
341 CXFA_FFApp* CXFA_WidgetAcc::GetApp()\r
342 {\r
343     return GetDoc()->GetApp();\r
344 }\r
345 IXFA_AppProvider* CXFA_WidgetAcc::GetAppProvider()\r
346 {\r
347     return GetApp()->GetAppProvider();\r
348 }\r
349 FX_INT32 CXFA_WidgetAcc::ProcessEvent(FX_INT32 iActivity, CXFA_EventParam* pEventParam)\r
350 {\r
351     if (this->GetClassID() == XFA_ELEMENT_Draw) {\r
352         return XFA_EVENTERROR_NotExist;\r
353     }\r
354     FX_INT32 iRet = XFA_EVENTERROR_NotExist;\r
355     CXFA_NodeArray eventArray;\r
356     FX_INT32 iCounts = GetEventByActivity(iActivity, eventArray, pEventParam->m_bIsFormReady);\r
357     for (FX_INT32 i = 0; i < iCounts; i++) {\r
358         CXFA_Event event(eventArray[i]);\r
359         FX_INT32 result = ProcessEvent(event, pEventParam);\r
360         if (i == 0) {\r
361             iRet = result;\r
362         } else if (result == XFA_EVENTERROR_Sucess) {\r
363             iRet = result;\r
364         }\r
365     }\r
366     return iRet;\r
367 }\r
368 FX_INT32 CXFA_WidgetAcc::ProcessEvent(CXFA_Event& event, CXFA_EventParam* pEventParam)\r
369 {\r
370     if (!event) {\r
371         return XFA_EVENTERROR_NotExist;\r
372     }\r
373     switch(event.GetEventType()) {\r
374         case XFA_ELEMENT_Execute:\r
375             break;\r
376         case XFA_ELEMENT_Script: {\r
377                 CXFA_Script script = event.GetScript();\r
378                 return ExecuteScript(script, pEventParam);\r
379             }\r
380             break;\r
381         case XFA_ELEMENT_SignData:\r
382             break;\r
383         case XFA_ELEMENT_Submit: {\r
384                 CXFA_Submit submit = event.GetSubmit();\r
385                 return GetDoc()->GetDocProvider()->SubmitData((XFA_HDOC)GetDoc(), submit);\r
386             }\r
387         default:\r
388             break;\r
389     }\r
390     return XFA_EVENTERROR_NotExist;\r
391 }\r
392 FX_INT32 CXFA_WidgetAcc::ProcessCalculate()\r
393 {\r
394     if (this->GetClassID() == XFA_ELEMENT_Draw) {\r
395         return XFA_EVENTERROR_NotExist;\r
396     }\r
397     CXFA_Calculate calc = this->GetCalculate();\r
398     if (!calc) {\r
399         return XFA_EVENTERROR_NotExist;\r
400     }\r
401     if (this->GetNode()->HasFlag(XFA_NODEFLAG_UserInteractive)) {\r
402         return XFA_EVENTERROR_Disabled;\r
403     }\r
404     CXFA_EventParam EventParam;\r
405     EventParam.m_eType = XFA_EVENT_Calculate;\r
406     CXFA_Script script = calc.GetScript();\r
407     FX_INT32 iRet = ExecuteScript(script, &EventParam);\r
408     if (iRet == XFA_EVENTERROR_Sucess) {\r
409         if (GetRawValue() != EventParam.m_wsResult) {\r
410             FX_BOOL bNotify = GetDoc()->GetDocType() == XFA_DOCTYPE_Static;\r
411             SetValue(EventParam.m_wsResult, XFA_VALUEPICTURE_Raw);\r
412             UpdateUIDisplay();\r
413             if (bNotify) {\r
414                 NotifyEvent(XFA_WIDGETEVENT_PostContentChanged, NULL, NULL, NULL);\r
415             }\r
416             iRet = XFA_EVENTERROR_Sucess;\r
417         }\r
418     }\r
419     return iRet;\r
420 }\r
421 void CXFA_WidgetAcc::ProcessScriptTestValidate(CXFA_Validate validate, FX_INT32 iRet, FXJSE_HVALUE pRetValue, FX_BOOL bVersionFlag)\r
422 {\r
423     if (iRet == XFA_EVENTERROR_Sucess && pRetValue) {\r
424         if (FXJSE_Value_IsBoolean(pRetValue) && !FXJSE_Value_ToBoolean(pRetValue)) {\r
425             IXFA_AppProvider* pAppProvider = GetAppProvider();\r
426             if (!pAppProvider) {\r
427                 return;\r
428             }\r
429             CFX_WideString wsTitle;\r
430             pAppProvider->LoadString(XFA_IDS_AppName, wsTitle);\r
431             CFX_WideString wsScriptMsg;\r
432             validate.GetScriptMessageText(wsScriptMsg);\r
433             FX_INT32 eScriptTest = validate.GetScriptTest();\r
434             if (eScriptTest == XFA_ATTRIBUTEENUM_Warning) {\r
435                 if (this->GetNode()->HasFlag(XFA_NODEFLAG_UserInteractive)) {\r
436                     return;\r
437                 }\r
438                 if (wsScriptMsg.IsEmpty()) {\r
439                     GetValidateMessage(pAppProvider, wsScriptMsg, FALSE, bVersionFlag);\r
440                 }\r
441                 if (bVersionFlag) {\r
442                     pAppProvider->MsgBox(wsScriptMsg, wsTitle, XFA_MBICON_Warning, XFA_MB_OK);\r
443                     return;\r
444                 }\r
445                 if (pAppProvider->MsgBox(wsScriptMsg, wsTitle, XFA_MBICON_Warning, XFA_MB_YesNo) == XFA_IDYes) {\r
446                     this->GetNode()->SetFlag(XFA_NODEFLAG_UserInteractive, TRUE, FALSE);\r
447                 }\r
448             } else {\r
449                 if (wsScriptMsg.IsEmpty()) {\r
450                     GetValidateMessage(pAppProvider, wsScriptMsg, TRUE, bVersionFlag);\r
451                 }\r
452                 pAppProvider->MsgBox(wsScriptMsg, wsTitle, XFA_MBICON_Error, XFA_MB_OK);\r
453             }\r
454         }\r
455     }\r
456 }\r
457 FX_INT32 CXFA_WidgetAcc::ProcessFormatTestValidate(CXFA_Validate validate, FX_BOOL bVersionFlag)\r
458 {\r
459     CFX_WideString wsRawValue = GetRawValue();\r
460     if (!wsRawValue.IsEmpty()) {\r
461         CFX_WideString wsPicture;\r
462         validate.GetPicture(wsPicture);\r
463         if (wsPicture.IsEmpty()) {\r
464             return XFA_EVENTERROR_NotExist;\r
465         }\r
466         IFX_Locale* pLocale = GetLocal();\r
467         if (!pLocale) {\r
468             return XFA_EVENTERROR_NotExist;\r
469         }\r
470         CXFA_LocaleValue lcValue = XFA_GetLocaleValue(this);\r
471         if (!lcValue.ValidateValue(lcValue.GetValue(), wsPicture, pLocale)) {\r
472             IXFA_AppProvider* pAppProvider = GetAppProvider();\r
473             if (!pAppProvider) {\r
474                 return XFA_EVENTERROR_NotExist;\r
475             }\r
476             CFX_WideString wsFormatMsg;\r
477             validate.GetFormatMessageText(wsFormatMsg);\r
478             CFX_WideString wsTitle;\r
479             pAppProvider->LoadString(XFA_IDS_AppName, wsTitle);\r
480             FX_INT32 eFormatTest = validate.GetFormatTest();\r
481             if (eFormatTest == XFA_ATTRIBUTEENUM_Error) {\r
482                 if (wsFormatMsg.IsEmpty()) {\r
483                     GetValidateMessage(pAppProvider, wsFormatMsg, TRUE, bVersionFlag);\r
484                 }\r
485                 pAppProvider->MsgBox(wsFormatMsg, wsTitle, XFA_MBICON_Error, XFA_MB_OK);\r
486                 return XFA_EVENTERROR_Sucess;\r
487             }\r
488             if (this->GetNode()->HasFlag(XFA_NODEFLAG_UserInteractive)) {\r
489                 return XFA_EVENTERROR_NotExist;\r
490             }\r
491             if (wsFormatMsg.IsEmpty()) {\r
492                 GetValidateMessage(pAppProvider, wsFormatMsg, FALSE, bVersionFlag);\r
493             }\r
494             if (bVersionFlag) {\r
495                 pAppProvider->MsgBox(wsFormatMsg, wsTitle, XFA_MBICON_Warning, XFA_MB_OK);\r
496                 return XFA_EVENTERROR_Sucess;\r
497             }\r
498             if (pAppProvider->MsgBox(wsFormatMsg, wsTitle, XFA_MBICON_Warning, XFA_MB_YesNo) == XFA_IDYes) {\r
499                 this->GetNode()->SetFlag(XFA_NODEFLAG_UserInteractive, TRUE, FALSE);\r
500             }\r
501             return XFA_EVENTERROR_Sucess;\r
502         }\r
503     }\r
504     return XFA_EVENTERROR_NotExist;\r
505 }\r
506 FX_INT32 CXFA_WidgetAcc::ProcessNullTestValidate(CXFA_Validate validate, FX_INT32 iFlags, FX_BOOL bVersionFlag)\r
507 {\r
508     CFX_WideString wsValue;\r
509     this->GetValue(wsValue, XFA_VALUEPICTURE_Raw);\r
510     if (!wsValue.IsEmpty()) {\r
511         return XFA_EVENTERROR_Sucess;\r
512     }\r
513     if (this->m_bIsNull && (this->m_bPreNull == this->m_bIsNull)) {\r
514         return XFA_EVENTERROR_Sucess;\r
515     }\r
516     FX_INT32 eNullTest = validate.GetNullTest();\r
517     CFX_WideString wsNullMsg;\r
518     validate.GetNullMessageText(wsNullMsg);\r
519     if (iFlags & 0x01) {\r
520         FX_INT32 iRet = XFA_EVENTERROR_Sucess;\r
521         if (eNullTest != XFA_ATTRIBUTEENUM_Disabled) {\r
522             iRet = XFA_EVENTERROR_Error;\r
523         }\r
524         if (!wsNullMsg.IsEmpty()) {\r
525             if (eNullTest != XFA_ATTRIBUTEENUM_Disabled) {\r
526                 m_pDocView->m_arrNullTestMsg.Add(wsNullMsg);\r
527                 return XFA_EVENTERROR_Error;\r
528             }\r
529             return XFA_EVENTERROR_Sucess;\r
530         }\r
531         return iRet;\r
532     }\r
533     if (wsNullMsg.IsEmpty() && bVersionFlag && eNullTest != XFA_ATTRIBUTEENUM_Disabled) {\r
534         return XFA_EVENTERROR_Error;\r
535     }\r
536     IXFA_AppProvider* pAppProvider = GetAppProvider();\r
537     if (!pAppProvider) {\r
538         return XFA_EVENTERROR_NotExist;\r
539     }\r
540     CFX_WideString wsCaptionName;\r
541     CFX_WideString wsTitle;\r
542     pAppProvider->LoadString(XFA_IDS_AppName, wsTitle);\r
543     switch (eNullTest) {\r
544         case XFA_ATTRIBUTEENUM_Error: {\r
545                 if (wsNullMsg.IsEmpty()) {\r
546                     GetValidateCaptionName(wsCaptionName, bVersionFlag);\r
547                     CFX_WideString wsError;\r
548                     pAppProvider->LoadString(XFA_IDS_ValidateNullError, wsError);\r
549                     wsNullMsg.Format(wsError, (FX_LPCWSTR)wsCaptionName);\r
550                 }\r
551                 pAppProvider->MsgBox(wsNullMsg, wsTitle, XFA_MBICON_Status, XFA_MB_OK);\r
552                 return XFA_EVENTERROR_Error;\r
553             }\r
554         case XFA_ATTRIBUTEENUM_Warning: {\r
555                 if (this->GetNode()->HasFlag(XFA_NODEFLAG_UserInteractive)) {\r
556                     return TRUE;\r
557                 }\r
558                 if (wsNullMsg.IsEmpty()) {\r
559                     GetValidateCaptionName(wsCaptionName, bVersionFlag);\r
560                     CFX_WideString wsWarning;\r
561                     pAppProvider->LoadString(XFA_IDS_ValidateNullWarning, wsWarning);\r
562                     wsNullMsg.Format(wsWarning, (FX_LPCWSTR)wsCaptionName, (FX_LPCWSTR)wsCaptionName);\r
563                 }\r
564                 if (pAppProvider->MsgBox(wsNullMsg, wsTitle, XFA_MBICON_Warning, XFA_MB_YesNo) == XFA_IDYes) {\r
565                     this->GetNode()->SetFlag(XFA_NODEFLAG_UserInteractive, TRUE, FALSE);\r
566                 }\r
567                 return XFA_EVENTERROR_Error;\r
568             }\r
569         case XFA_ATTRIBUTEENUM_Disabled:\r
570         default:\r
571             break;\r
572     }\r
573     return XFA_EVENTERROR_Sucess;\r
574 }\r
575 void CXFA_WidgetAcc::GetValidateCaptionName(CFX_WideString& wsCaptionName, FX_BOOL bVersionFlag)\r
576 {\r
577     if (!bVersionFlag) {\r
578         CXFA_Caption caption = GetCaption();\r
579         if (caption) {\r
580             CXFA_Value capValue = caption.GetValue();\r
581             if (capValue) {\r
582                 CXFA_Text capText = capValue.GetText();\r
583                 if (capText) {\r
584                     capText.GetContent(wsCaptionName);\r
585                 }\r
586             }\r
587         }\r
588     }\r
589     if (wsCaptionName.IsEmpty()) {\r
590         GetName(wsCaptionName);\r
591     }\r
592 }\r
593 void CXFA_WidgetAcc::GetValidateMessage(IXFA_AppProvider* pAppProvider, CFX_WideString& wsMessage, FX_BOOL bError, FX_BOOL bVersionFlag)\r
594 {\r
595     CFX_WideString wsCaptionName;\r
596     GetValidateCaptionName(wsCaptionName, bVersionFlag);\r
597     CFX_WideString wsError;\r
598     if (bVersionFlag) {\r
599         pAppProvider->LoadString(XFA_IDS_ValidateFailed, wsError);\r
600         wsMessage.Format(wsError, (FX_LPCWSTR)wsCaptionName);\r
601         return;\r
602     }\r
603     if (bError) {\r
604         pAppProvider->LoadString(XFA_IDS_ValidateError, wsError);\r
605         wsMessage.Format(wsError, (FX_LPCWSTR)wsCaptionName);\r
606         return;\r
607     }\r
608     CFX_WideString wsWarning;\r
609     pAppProvider->LoadString(XFA_IDS_ValidateWarning, wsWarning);\r
610     wsMessage.Format(wsWarning, (FX_LPCWSTR)wsCaptionName, (FX_LPCWSTR)wsCaptionName);\r
611 }\r
612 FX_INT32 CXFA_WidgetAcc::ProcessValidate(FX_INT32 iFlags)\r
613 {\r
614     if (this->GetClassID() == XFA_ELEMENT_Draw) {\r
615         return XFA_EVENTERROR_NotExist;\r
616     }\r
617     CXFA_Validate validate = this->GetValidate();\r
618     if (!validate) {\r
619         return XFA_EVENTERROR_NotExist;\r
620     }\r
621     FX_BOOL bInitDoc = ((CXFA_Node*)validate)->HasFlag(XFA_NODEFLAG_NeedsInitApp);\r
622     FX_BOOL bStatus = m_pDocView->GetLayoutStatus() < XFA_DOCVIEW_LAYOUTSTATUS_End;\r
623     FX_INT32 iFormat = 0;\r
624     FXJSE_HVALUE pRetValue = NULL;\r
625     FX_INT32  iRet = XFA_EVENTERROR_NotExist;\r
626     CXFA_Script script = validate.GetScript();\r
627     if (script) {\r
628         CXFA_EventParam eParam;\r
629         eParam.m_eType = XFA_EVENT_Validate;\r
630         eParam.m_pTarget = this;\r
631         iRet = ExecuteScript(script, &eParam, ((bInitDoc || bStatus) && this->GetRawValue().IsEmpty()) ? NULL : &pRetValue);\r
632     }\r
633     XFA_VERSION version = GetDoc()->GetXFADoc()->GetCurVersionMode();\r
634     FX_BOOL bVersionFlag = FALSE;\r
635     if (version < XFA_VERSION_208) {\r
636         bVersionFlag = TRUE;\r
637     }\r
638     if (bInitDoc) {\r
639         ((CXFA_Node*)validate)->SetFlag(XFA_NODEFLAG_NeedsInitApp, FALSE, FALSE);\r
640     } else {\r
641         iFormat = ProcessFormatTestValidate(validate, bVersionFlag);\r
642         if (!bVersionFlag) {\r
643             bVersionFlag = GetDoc()->GetXFADoc()->HasFlag(XFA_DOCFLAG_Scripting);\r
644         }\r
645         iRet |= ProcessNullTestValidate(validate, iFlags, bVersionFlag);\r
646     }\r
647     if (iFormat != XFA_EVENTERROR_Sucess) {\r
648         ProcessScriptTestValidate(validate, iRet, pRetValue, bVersionFlag);\r
649     }\r
650     if (pRetValue) {\r
651         FXJSE_Value_Release(pRetValue);\r
652     }\r
653     return iRet | iFormat;\r
654 }\r
655 FX_INT32 CXFA_WidgetAcc::ExecuteScript(CXFA_Script script, CXFA_EventParam* pEventParam, FXJSE_HVALUE* pRetValue)\r
656 {\r
657     FXSYS_assert(pEventParam);\r
658     if (!script) {\r
659         return XFA_EVENTERROR_NotExist;\r
660     }\r
661     if(script.GetRunAt() == XFA_ATTRIBUTEENUM_Server) {\r
662         return XFA_EVENTERROR_Disabled;\r
663     }\r
664     CFX_WideString wsExpression;\r
665     script.GetExpression(wsExpression);\r
666     if (wsExpression.IsEmpty()) {\r
667         return XFA_EVENTERROR_NotExist;\r
668     }\r
669     XFA_SCRIPTTYPE eScriptType = script.GetContentType();\r
670     if (eScriptType == XFA_SCRIPTTYPE_Unkown) {\r
671         return XFA_EVENTERROR_Sucess;\r
672     }\r
673     CXFA_FFDoc* pDoc = GetDoc();\r
674     IXFA_ScriptContext* pContext = pDoc->GetXFADoc()->GetScriptContext();\r
675     pContext->SetEventParam(pEventParam);\r
676     pContext->SetRunAtType((XFA_ATTRIBUTEENUM)script.GetRunAt());\r
677     CXFA_NodeArray refNodes;\r
678     if (pEventParam->m_eType == XFA_EVENT_InitCalculate || pEventParam->m_eType == XFA_EVENT_Calculate) {\r
679         pContext->SetNodesOfRunScript(&refNodes);\r
680     }\r
681     FXJSE_HVALUE hRetValue = FXJSE_Value_Create(pContext->GetRuntime());\r
682     FX_BOOL bRet = FALSE;\r
683     bRet = pContext->RunScript((XFA_SCRIPTLANGTYPE)eScriptType, wsExpression, hRetValue, m_pNode);\r
684     FX_INT32 iRet = XFA_EVENTERROR_Error;\r
685     if (bRet) {\r
686         iRet = XFA_EVENTERROR_Sucess;\r
687         if (pEventParam->m_eType == XFA_EVENT_Calculate || pEventParam->m_eType == XFA_EVENT_InitCalculate) {\r
688             if (!FXJSE_Value_IsUndefined(hRetValue)) {\r
689                 if (!FXJSE_Value_IsNull(hRetValue)) {\r
690                     CFX_ByteString bsString;\r
691                     FXJSE_Value_ToUTF8String(hRetValue, bsString);\r
692                     pEventParam->m_wsResult = CFX_WideString::FromUTF8(bsString, bsString.GetLength());\r
693                 }\r
694                 iRet = XFA_EVENTERROR_Sucess;\r
695             } else {\r
696                 iRet = XFA_EVENTERROR_Error;\r
697             }\r
698             if (pEventParam->m_eType == XFA_EVENT_InitCalculate) {\r
699                 if ((iRet == XFA_EVENTERROR_Sucess) && (GetRawValue() != pEventParam->m_wsResult)) {\r
700                     SetValue(pEventParam->m_wsResult, XFA_VALUEPICTURE_Raw);\r
701                     m_pDocView->AddValidateWidget(this);\r
702                 }\r
703             }\r
704             FX_INT32 iRefs = refNodes.GetSize();\r
705             for (FX_INT32 r = 0; r < iRefs; r++) {\r
706                 CXFA_WidgetAcc* pRefAcc = (CXFA_WidgetAcc*)refNodes[r]->GetWidgetData();\r
707                 if (pRefAcc && pRefAcc == this) {\r
708                     continue;\r
709                 }\r
710                 CXFA_Node* pRefNode = refNodes[r];\r
711                 CXFA_CalcData* pGlobalData = (CXFA_CalcData*)pRefNode->GetUserData(XFA_CalcData);\r
712                 if (!pGlobalData) {\r
713                     pGlobalData = FX_NEW CXFA_CalcData;\r
714                     pRefNode->SetUserData(XFA_CalcData, pGlobalData, &gs_XFADeleteCalcData);\r
715                 }\r
716                 if (pGlobalData->m_Globals.Find(this) < 0) {\r
717                     pGlobalData->m_Globals.Add(this);\r
718                 }\r
719             }\r
720         }\r
721     }\r
722     if (pRetValue) {\r
723         *pRetValue = hRetValue;\r
724     } else {\r
725         FXJSE_Value_Release(hRetValue);\r
726     }\r
727     pContext->SetNodesOfRunScript(NULL);\r
728     return iRet;\r
729 }\r
730 CXFA_FFWidget* CXFA_WidgetAcc::GetNextWidget(CXFA_FFWidget* pWidget)\r
731 {\r
732     CXFA_LayoutItem* pLayout = NULL;\r
733     if (pWidget) {\r
734         pLayout = pWidget->GetLayoutItem()->GetNext();\r
735     } else {\r
736         pLayout = m_pDocView->GetXFALayout()->GetLayoutItem(m_pNode);\r
737     }\r
738     return (CXFA_FFWidget*)(CXFA_ContentLayoutItemImpl*)pLayout;\r
739 }\r
740 void CXFA_WidgetAcc::UpdateUIDisplay(CXFA_FFWidget* pExcept )\r
741 {\r
742     CXFA_FFWidget* pWidget = NULL;\r
743     while ((pWidget = this->GetNextWidget(pWidget)) != NULL) {\r
744         if (pWidget == pExcept || !pWidget->IsLoaded() || (GetUIType() != XFA_ELEMENT_CheckButton && pWidget->IsFocused())) {\r
745             continue;\r
746         }\r
747         pWidget->UpdateFWLData();\r
748         pWidget->AddInvalidateRect();\r
749     }\r
750 }\r
751 void CXFA_WidgetAcc::NotifyEvent(FX_DWORD dwEvent, CXFA_FFWidget* pWidget , FX_LPVOID pParam , FX_LPVOID pAdditional )\r
752 {\r
753     IXFA_DocProvider* pDocProvider = GetDoc()->GetDocProvider();\r
754     if (pWidget) {\r
755         pDocProvider->WidgetEvent((XFA_HWIDGET)pWidget, this, dwEvent, pParam, pAdditional);\r
756     } else {\r
757         pWidget = GetNextWidget(pWidget);\r
758         if (pWidget == NULL) {\r
759             pDocProvider->WidgetEvent(NULL, this, dwEvent, pParam, pAdditional);\r
760             return;\r
761         }\r
762         while (pWidget) {\r
763             pDocProvider->WidgetEvent((XFA_HWIDGET)pWidget, this, dwEvent, pParam, pAdditional);\r
764             pWidget = GetNextWidget(pWidget);\r
765         }\r
766     }\r
767 }\r
768 void CXFA_WidgetAcc::CalcCaptionSize(CFX_SizeF &szCap)\r
769 {\r
770     CXFA_Caption caption = this->GetCaption();\r
771     if (!caption.IsExistInXML() || caption.GetPresence() != XFA_ATTRIBUTEENUM_Visible) {\r
772         return;\r
773     }\r
774     LoadCaption();\r
775     XFA_ELEMENT eUIType = (XFA_ELEMENT)GetUIType();\r
776     FX_INT32 iCapPlacement = caption.GetPlacementType();\r
777     FX_FLOAT fCapReserve = caption.GetReserve();\r
778     FX_BOOL bVert = iCapPlacement == XFA_ATTRIBUTEENUM_Top || iCapPlacement == XFA_ATTRIBUTEENUM_Bottom;\r
779     FX_BOOL bReserveExit = fCapReserve > 0.01;\r
780     CXFA_TextLayout* pCapTextLayout = ((CXFA_FieldLayoutData*)m_pLayoutData)->m_pCapTextLayout;\r
781     if (pCapTextLayout) {\r
782         if (!bVert && eUIType != XFA_ELEMENT_Button) {\r
783             szCap.x = fCapReserve;\r
784         }\r
785         CFX_SizeF minSize;\r
786         minSize.Set(0, 0);\r
787         pCapTextLayout->CalcSize(minSize, szCap, szCap);\r
788         if (bReserveExit) {\r
789             bVert ? szCap.y = fCapReserve : szCap.x = fCapReserve;\r
790         }\r
791     } else {\r
792         FX_FLOAT fFontSize = 10.0f;\r
793         if (CXFA_Font font = caption.GetFont()) {\r
794             fFontSize = font.GetFontSize();\r
795         } else if (CXFA_Font widgetfont = GetFont()) {\r
796             fFontSize = widgetfont.GetFontSize();\r
797         }\r
798         if (bVert) {\r
799             szCap.y = fCapReserve > 0 ? fCapReserve : fFontSize;\r
800         } else {\r
801             szCap.x = fCapReserve > 0 ? fCapReserve : 0;\r
802             szCap.y = fFontSize;\r
803         }\r
804     }\r
805     if (CXFA_Margin mgCap = caption.GetMargin()) {\r
806         FX_FLOAT fLeftInset, fTopInset, fRightInset, fBottomInset;\r
807         mgCap.GetLeftInset(fLeftInset);\r
808         mgCap.GetTopInset(fTopInset);\r
809         mgCap.GetRightInset(fRightInset);\r
810         mgCap.GetBottomInset(fBottomInset);\r
811         if (bReserveExit) {\r
812             bVert ? (szCap.x += fLeftInset + fRightInset) : (szCap.y += fTopInset + fBottomInset);\r
813         } else {\r
814             szCap.x += fLeftInset + fRightInset;\r
815             szCap.y += fTopInset + fBottomInset;\r
816         }\r
817     }\r
818 }\r
819 FX_BOOL CXFA_WidgetAcc::CalculateFieldAutoSize(CFX_SizeF &size)\r
820 {\r
821     CFX_SizeF szCap;\r
822     szCap.Set(0, 0);\r
823     CalcCaptionSize(szCap);\r
824     CFX_RectF rtUIMargin;\r
825     GetUIMargin(rtUIMargin);\r
826     size.x += rtUIMargin.left + rtUIMargin.width;\r
827     size.y += rtUIMargin.top + rtUIMargin.height;\r
828     if (szCap.x > 0 && szCap.y > 0) {\r
829         FX_INT32 iCapPlacement = this->GetCaption().GetPlacementType();\r
830         switch(iCapPlacement) {\r
831             case XFA_ATTRIBUTEENUM_Left:\r
832             case XFA_ATTRIBUTEENUM_Right:\r
833             case XFA_ATTRIBUTEENUM_Inline: {\r
834                     size.x += szCap.x;\r
835                     size.y = FX_MAX(size.y, szCap.y);\r
836                 }\r
837                 break;\r
838             case XFA_ATTRIBUTEENUM_Top:\r
839             case XFA_ATTRIBUTEENUM_Bottom: {\r
840                     size.y += szCap.y;\r
841                     size.x = FX_MAX(size.x, szCap.x);\r
842                 }\r
843             default:\r
844                 break;\r
845         }\r
846     }\r
847     return CalculateWidgetAutoSize(size);\r
848 }\r
849 FX_BOOL CXFA_WidgetAcc::CalculateWidgetAutoSize(CFX_SizeF &size)\r
850 {\r
851     CXFA_Margin mgWidget = this->GetMargin();\r
852     if (mgWidget.IsExistInXML()) {\r
853         FX_FLOAT fLeftInset, fTopInset, fRightInset, fBottomInset;\r
854         mgWidget.GetLeftInset(fLeftInset);\r
855         mgWidget.GetTopInset(fTopInset);\r
856         mgWidget.GetRightInset(fRightInset);\r
857         mgWidget.GetBottomInset(fBottomInset);\r
858         size.x += fLeftInset + fRightInset;\r
859         size.y += fTopInset + fBottomInset;\r
860     }\r
861     CXFA_Para para = this->GetPara();\r
862     if (para.IsExistInXML()) {\r
863         size.x += para.GetMarginLeft();\r
864         size.x += para.GetTextIndent();\r
865     }\r
866     FX_FLOAT fVal = 0, fMin = 0, fMax = 0;\r
867     if (this->GetWidth(fVal)) {\r
868         size.x = fVal;\r
869     } else {\r
870         if (this->GetMinWidth(fMin)) {\r
871             size.x = FX_MAX(size.x, fMin);\r
872         }\r
873         if (this->GetMaxWidth(fMax) && fMax > 0) {\r
874             size.x = FX_MIN(size.x, fMax);\r
875         }\r
876     }\r
877     fVal = 0, fMin = 0, fMax = 0;\r
878     if (this->GetHeight(fVal)) {\r
879         size.y = fVal;\r
880     } else {\r
881         if (this->GetMinHeight(fMin)) {\r
882             size.y = FX_MAX(size.y, fMin);\r
883         }\r
884         if (this->GetMaxHeight(fMax) && fMax > 0) {\r
885             size.y = FX_MIN(size.y, fMax);\r
886         }\r
887     }\r
888     return TRUE;\r
889 }\r
890 void CXFA_WidgetAcc::CalculateTextContentSize(CFX_SizeF &size)\r
891 {\r
892     FX_FLOAT fFontSize = GetFontSize();\r
893     CFX_WideString wsText;\r
894     this->GetValue(wsText, XFA_VALUEPICTURE_Display);\r
895     if (wsText.IsEmpty()) {\r
896         size.y += fFontSize;\r
897         return;\r
898     }\r
899     FX_WCHAR wcEnter = '\n';\r
900     FX_WCHAR wsLast = wsText.GetAt(wsText.GetLength() - 1);\r
901     if(wsLast == wcEnter) {\r
902         wsText = wsText + wcEnter;\r
903     }\r
904     if (!((CXFA_FieldLayoutData*)m_pLayoutData)->m_pTextOut) {\r
905         ((CXFA_FieldLayoutData*)m_pLayoutData)->m_pTextOut = IFDE_TextOut::Create();\r
906         IFDE_TextOut* pTextOut = ((CXFA_FieldLayoutData*)m_pLayoutData)->m_pTextOut;\r
907         pTextOut->SetFont(GetFDEFont());\r
908         pTextOut->SetFontSize(fFontSize);\r
909         pTextOut->SetLineBreakTolerance(fFontSize * 0.2f);\r
910         pTextOut->SetLineSpace(GetLineHeight());\r
911         FX_DWORD dwStyles = FDE_TTOSTYLE_LastLineHeight;\r
912         if (GetUIType() == XFA_ELEMENT_TextEdit && IsMultiLine()) {\r
913             dwStyles |= FDE_TTOSTYLE_LineWrap;\r
914         }\r
915         pTextOut->SetStyles(dwStyles);\r
916     }\r
917     ((CXFA_FieldLayoutData*)m_pLayoutData)->m_pTextOut->CalcLogicSize(wsText, wsText.GetLength(), size);\r
918 }\r
919 FX_BOOL CXFA_WidgetAcc::CalculateTextEditAutoSize(CFX_SizeF &size)\r
920 {\r
921     if (size.x > 0) {\r
922         CFX_SizeF szOrz = size;\r
923         CFX_SizeF szCap;\r
924         szCap.Set(0, 0);\r
925         CalcCaptionSize(szCap);\r
926         FX_BOOL bCapExit = szCap.x > 0.01 && szCap.y > 0.01;\r
927         FX_INT32 iCapPlacement = XFA_ATTRIBUTEENUM_Unknown;\r
928         if (bCapExit) {\r
929             iCapPlacement = this->GetCaption().GetPlacementType();\r
930             switch(iCapPlacement) {\r
931                 case XFA_ATTRIBUTEENUM_Left:\r
932                 case XFA_ATTRIBUTEENUM_Right:\r
933                 case XFA_ATTRIBUTEENUM_Inline: {\r
934                         size.x -= szCap.x;\r
935                     }\r
936                 default:\r
937                     break;\r
938             }\r
939         }\r
940         CFX_RectF rtUIMargin;\r
941         GetUIMargin(rtUIMargin);\r
942         size.x -= rtUIMargin.left + rtUIMargin.width;\r
943         CXFA_Margin mgWidget = this->GetMargin();\r
944         if (mgWidget.IsExistInXML()) {\r
945             FX_FLOAT fLeftInset, fRightInset;\r
946             mgWidget.GetLeftInset(fLeftInset);\r
947             mgWidget.GetRightInset(fRightInset);\r
948             size.x -= fLeftInset + fRightInset;\r
949         }\r
950         CalculateTextContentSize(size);\r
951         size.y += rtUIMargin.top + rtUIMargin.height;\r
952         if (bCapExit) {\r
953             switch(iCapPlacement) {\r
954                 case XFA_ATTRIBUTEENUM_Left:\r
955                 case XFA_ATTRIBUTEENUM_Right:\r
956                 case XFA_ATTRIBUTEENUM_Inline: {\r
957                         size.y = FX_MAX(size.y, szCap.y);\r
958                     }\r
959                     break;\r
960                 case XFA_ATTRIBUTEENUM_Top:\r
961                 case XFA_ATTRIBUTEENUM_Bottom: {\r
962                         size.y += szCap.y;\r
963                     }\r
964                 default:\r
965                     break;\r
966             }\r
967         }\r
968         size.x = szOrz.x;\r
969         return CalculateWidgetAutoSize(size);\r
970     }\r
971     CalculateTextContentSize(size);\r
972     return CalculateFieldAutoSize(size);\r
973 }\r
974 FX_BOOL CXFA_WidgetAcc::CalculateCheckButtonAutoSize(CFX_SizeF &size)\r
975 {\r
976     FX_FLOAT fCheckSize = this->GetCheckButtonSize();\r
977     size.x = size.y = fCheckSize;\r
978     return CalculateFieldAutoSize(size);\r
979 }\r
980 FX_BOOL CXFA_WidgetAcc::CalculatePushButtonAutoSize(CFX_SizeF &size)\r
981 {\r
982     CalcCaptionSize(size);\r
983     return CalculateWidgetAutoSize(size);\r
984 }\r
985 FX_BOOL CXFA_WidgetAcc::CalculateImageAutoSize(CFX_SizeF &size)\r
986 {\r
987     if (!GetImageImage()) {\r
988         LoadImageImage();\r
989     }\r
990     size.Set(0, 0);\r
991     if (CFX_DIBitmap* pBitmap = GetImageImage()) {\r
992         CXFA_Image imageObj = GetFormValue().GetImage();\r
993         CFX_RectF rtImage, rtFit;\r
994         rtImage.Set(0, 0, 0, 0);\r
995         rtFit.Set(0, 0, 0, 0);\r
996         FX_INT32 iImageXDpi = 0;\r
997         FX_INT32 iImageYDpi = 0;\r
998         GetImageDpi(iImageXDpi, iImageYDpi);\r
999         rtImage.width = XFA_UnitPx2Pt((FX_FLOAT)pBitmap->GetWidth(), (FX_FLOAT)iImageXDpi);\r
1000         rtImage.height = XFA_UnitPx2Pt((FX_FLOAT)pBitmap->GetHeight(), (FX_FLOAT)iImageYDpi);\r
1001         if(GetWidth(rtFit.width)) {\r
1002             GetWidthWithoutMargin(rtFit.width);\r
1003         } else {\r
1004             rtFit.width = rtImage.width;\r
1005         }\r
1006         if(GetHeight(rtFit.height)) {\r
1007             GetHeightWithoutMargin(rtFit.height);\r
1008         } else {\r
1009             rtFit.height = rtImage.height;\r
1010         }\r
1011         size.x = rtFit.width;\r
1012         size.y = rtFit.height;\r
1013     }\r
1014     return CalculateWidgetAutoSize(size);\r
1015 }\r
1016 FX_BOOL CXFA_WidgetAcc::CalculateImageEditAutoSize(CFX_SizeF &size)\r
1017 {\r
1018     if (!GetImageEditImage()) {\r
1019         LoadImageEditImage();\r
1020     }\r
1021     size.Set(0, 0);\r
1022     if (CFX_DIBitmap* pBitmap = GetImageEditImage()) {\r
1023         CFX_RectF rtImage, rtFit;\r
1024         rtImage.Set(0, 0, 0, 0);\r
1025         rtFit.Set(0, 0, 0, 0);\r
1026         FX_INT32 iImageXDpi = 0;\r
1027         FX_INT32 iImageYDpi = 0;\r
1028         GetImageEditDpi(iImageXDpi, iImageYDpi);\r
1029         rtImage.width = XFA_UnitPx2Pt((FX_FLOAT)pBitmap->GetWidth(), (FX_FLOAT)iImageXDpi);\r
1030         rtImage.height = XFA_UnitPx2Pt((FX_FLOAT)pBitmap->GetHeight(), (FX_FLOAT)iImageYDpi);\r
1031         if(GetWidth(rtFit.width)) {\r
1032             GetWidthWithoutMargin(rtFit.width);\r
1033         } else {\r
1034             rtFit.width = rtImage.width;\r
1035         }\r
1036         if(GetHeight(rtFit.height)) {\r
1037             GetHeightWithoutMargin(rtFit.height);\r
1038         } else {\r
1039             rtFit.height = rtImage.height;\r
1040         }\r
1041         size.x = rtFit.width;\r
1042         size.y = rtFit.height;\r
1043     }\r
1044     return CalculateFieldAutoSize(size);\r
1045 }\r
1046 FX_BOOL CXFA_WidgetAcc::LoadImageImage()\r
1047 {\r
1048     InitLayoutData();\r
1049     return ((CXFA_ImageLayoutData*)m_pLayoutData)->LoadImageData(this);\r
1050 }\r
1051 FX_BOOL CXFA_WidgetAcc::LoadImageEditImage()\r
1052 {\r
1053     InitLayoutData();\r
1054     return ((CXFA_ImageEditData*)m_pLayoutData)->LoadImageData(this);\r
1055 }\r
1056 void CXFA_WidgetAcc::GetImageDpi(FX_INT32 &iImageXDpi, FX_INT32 &iImageYDpi)\r
1057 {\r
1058     iImageXDpi = ((CXFA_ImageLayoutData*)m_pLayoutData)->m_iImageXDpi;\r
1059     iImageYDpi = ((CXFA_ImageLayoutData*)m_pLayoutData)->m_iImageYDpi;\r
1060 }\r
1061 void CXFA_WidgetAcc::GetImageEditDpi(FX_INT32 &iImageXDpi, FX_INT32 &iImageYDpi)\r
1062 {\r
1063     iImageXDpi = ((CXFA_ImageEditData*)m_pLayoutData)->m_iImageXDpi;\r
1064     iImageYDpi = ((CXFA_ImageEditData*)m_pLayoutData)->m_iImageYDpi;\r
1065 }\r
1066 FX_BOOL CXFA_WidgetAcc::CalculateTextAutoSize(CFX_SizeF &size)\r
1067 {\r
1068     if (!LoadText()) {\r
1069         return FALSE;\r
1070     }\r
1071     CXFA_TextLayout* pTextLayout = ((CXFA_TextLayoutData*)m_pLayoutData)->m_pTextLayout;\r
1072     if (pTextLayout) {\r
1073         size.x = pTextLayout->StartLayout(size.x);\r
1074         size.y = pTextLayout->GetLayoutHeight();\r
1075     }\r
1076     return CalculateWidgetAutoSize(size);\r
1077 }\r
1078 FX_BOOL CXFA_WidgetAcc::LoadText()\r
1079 {\r
1080     InitLayoutData();\r
1081     return ((CXFA_TextLayoutData*)m_pLayoutData)->LoadText(this);\r
1082 }\r
1083 FX_FLOAT CXFA_WidgetAcc::CalculateWidgetAutoWidth(FX_FLOAT fWidthCalc)\r
1084 {\r
1085     CXFA_Margin mgWidget = this->GetMargin();\r
1086     if (mgWidget.IsExistInXML()) {\r
1087         FX_FLOAT fLeftInset, fRightInset;\r
1088         mgWidget.GetLeftInset(fLeftInset);\r
1089         mgWidget.GetRightInset(fRightInset);\r
1090         fWidthCalc += fLeftInset + fRightInset;\r
1091     }\r
1092     FX_FLOAT fMin = 0, fMax = 0;\r
1093     if (this->GetMinWidth(fMin)) {\r
1094         fWidthCalc = FX_MAX(fWidthCalc, fMin);\r
1095     }\r
1096     if (this->GetMaxWidth(fMax) && fMax > 0) {\r
1097         fWidthCalc = FX_MIN(fWidthCalc, fMax);\r
1098     }\r
1099     return fWidthCalc;\r
1100 }\r
1101 FX_FLOAT CXFA_WidgetAcc::GetWidthWithoutMargin(FX_FLOAT fWidthCalc)\r
1102 {\r
1103     CXFA_Margin mgWidget = this->GetMargin();\r
1104     if (mgWidget.IsExistInXML()) {\r
1105         FX_FLOAT fLeftInset, fRightInset;\r
1106         mgWidget.GetLeftInset(fLeftInset);\r
1107         mgWidget.GetRightInset(fRightInset);\r
1108         fWidthCalc -= fLeftInset + fRightInset;\r
1109     }\r
1110     return fWidthCalc;\r
1111 }\r
1112 FX_FLOAT CXFA_WidgetAcc::CalculateWidgetAutoHeight(FX_FLOAT fHeightCalc)\r
1113 {\r
1114     CXFA_Margin mgWidget = this->GetMargin();\r
1115     if (mgWidget.IsExistInXML()) {\r
1116         FX_FLOAT fTopInset, fBottomInset;\r
1117         mgWidget.GetTopInset(fTopInset);\r
1118         mgWidget.GetBottomInset(fBottomInset);\r
1119         fHeightCalc += fTopInset + fBottomInset;\r
1120     }\r
1121     FX_FLOAT fMin = 0, fMax = 0;\r
1122     if (this->GetMinHeight(fMin)) {\r
1123         fHeightCalc = FX_MAX(fHeightCalc, fMin);\r
1124     }\r
1125     if (this->GetMaxHeight(fMax) && fMax > 0) {\r
1126         fHeightCalc = FX_MIN(fHeightCalc, fMax);\r
1127     }\r
1128     return fHeightCalc;\r
1129 }\r
1130 FX_FLOAT CXFA_WidgetAcc::GetHeightWithoutMargin(FX_FLOAT fHeightCalc)\r
1131 {\r
1132     CXFA_Margin mgWidget = this->GetMargin();\r
1133     if (mgWidget.IsExistInXML()) {\r
1134         FX_FLOAT fTopInset, fBottomInset;\r
1135         mgWidget.GetTopInset(fTopInset);\r
1136         mgWidget.GetBottomInset(fBottomInset);\r
1137         fHeightCalc -= fTopInset + fBottomInset;\r
1138     }\r
1139     return fHeightCalc;\r
1140 }\r
1141 void CXFA_WidgetAcc::StartWidgetLayout(FX_FLOAT &fCalcWidth, FX_FLOAT& fCalcHeight)\r
1142 {\r
1143     InitLayoutData();\r
1144     XFA_ELEMENT eUIType = GetUIType();\r
1145     if (eUIType == XFA_ELEMENT_Text) {\r
1146         m_pLayoutData->m_fWidgetHeight = -1;\r
1147         GetHeight(m_pLayoutData->m_fWidgetHeight);\r
1148         StartTextLayout(fCalcWidth, fCalcHeight);\r
1149         return;\r
1150     }\r
1151     if (fCalcWidth > 0 && fCalcHeight > 0) {\r
1152         return;\r
1153     }\r
1154     m_pLayoutData->m_fWidgetHeight = -1;\r
1155     FX_FLOAT fWidth = 0;\r
1156     if (fCalcWidth > 0 && fCalcHeight < 0) {\r
1157         if (!GetHeight(fCalcHeight)) {\r
1158             CalculateAccWidthAndHeight(eUIType, fCalcWidth, fCalcHeight);\r
1159         }\r
1160         m_pLayoutData->m_fWidgetHeight = fCalcHeight;\r
1161         return;\r
1162     }\r
1163     if (fCalcWidth < 0 && fCalcHeight < 0) {\r
1164         if (!GetWidth(fWidth) || !GetHeight(fCalcHeight)) {\r
1165             CalculateAccWidthAndHeight(eUIType, fWidth, fCalcHeight);\r
1166         }\r
1167         fCalcWidth = fWidth;\r
1168     }\r
1169     m_pLayoutData->m_fWidgetHeight = fCalcHeight;\r
1170 }\r
1171 void CXFA_WidgetAcc::CalculateAccWidthAndHeight(XFA_ELEMENT eUIType, FX_FLOAT& fWidth, FX_FLOAT& fCalcHeight)\r
1172 {\r
1173     CFX_SizeF sz;\r
1174     sz.Set(fWidth, m_pLayoutData->m_fWidgetHeight);\r
1175     switch(eUIType) {\r
1176         case XFA_ELEMENT_Barcode:\r
1177         case XFA_ELEMENT_ChoiceList:\r
1178         case XFA_ELEMENT_Signature:\r
1179             CalculateFieldAutoSize(sz);\r
1180             break;\r
1181         case XFA_ELEMENT_ImageEdit:\r
1182             CalculateImageEditAutoSize(sz);\r
1183             break;\r
1184         case XFA_ELEMENT_Button:\r
1185             CalculatePushButtonAutoSize(sz);\r
1186             break;\r
1187         case XFA_ELEMENT_CheckButton:\r
1188             CalculateCheckButtonAutoSize(sz);\r
1189             break;\r
1190         case XFA_ELEMENT_DateTimeEdit:\r
1191         case XFA_ELEMENT_NumericEdit:\r
1192         case XFA_ELEMENT_PasswordEdit:\r
1193         case XFA_ELEMENT_TextEdit:\r
1194             CalculateTextEditAutoSize(sz);\r
1195             break;\r
1196         case XFA_ELEMENT_Image:\r
1197             CalculateImageAutoSize(sz);\r
1198             break;\r
1199         case XFA_ELEMENT_Arc:\r
1200         case XFA_ELEMENT_Line:\r
1201         case XFA_ELEMENT_Rectangle:\r
1202         case XFA_ELEMENT_Subform:\r
1203         case XFA_ELEMENT_ExclGroup:\r
1204             CalculateWidgetAutoSize(sz);\r
1205             break;\r
1206         default:\r
1207             break;\r
1208     }\r
1209     fWidth = sz.x;\r
1210     m_pLayoutData->m_fWidgetHeight = sz.y;\r
1211     fCalcHeight = sz.y;\r
1212 }\r
1213 FX_BOOL CXFA_WidgetAcc::FindSplitPos(FX_INT32 iBlockIndex, FX_FLOAT &fCalcHeight)\r
1214 {\r
1215     XFA_ELEMENT eUIType = (XFA_ELEMENT)GetUIType();\r
1216     if (eUIType == XFA_ELEMENT_Subform) {\r
1217         return FALSE;\r
1218     }\r
1219     if (eUIType != XFA_ELEMENT_Text && eUIType != XFA_ELEMENT_TextEdit && eUIType != XFA_ELEMENT_NumericEdit && eUIType != XFA_ELEMENT_PasswordEdit) {\r
1220         fCalcHeight = 0;\r
1221         return TRUE;\r
1222     }\r
1223     FX_FLOAT fTopInset = 0;\r
1224     FX_FLOAT fBottomInset = 0;\r
1225     if (iBlockIndex == 0) {\r
1226         CXFA_Margin mgWidget = this->GetMargin();\r
1227         if (mgWidget.IsExistInXML()) {\r
1228             mgWidget.GetTopInset(fTopInset);\r
1229             mgWidget.GetBottomInset(fBottomInset);\r
1230         }\r
1231         CFX_RectF rtUIMargin;\r
1232         this->GetUIMargin(rtUIMargin);\r
1233         fTopInset += rtUIMargin.top;\r
1234         fBottomInset += rtUIMargin.width;\r
1235     }\r
1236     if (eUIType == XFA_ELEMENT_Text) {\r
1237         FX_FLOAT fHeight = fCalcHeight;\r
1238         if (iBlockIndex == 0) {\r
1239             fCalcHeight = fCalcHeight - fTopInset;\r
1240             if (fCalcHeight < 0) {\r
1241                 fCalcHeight = 0;\r
1242             }\r
1243         }\r
1244         CXFA_TextLayout* pTextLayout = ((CXFA_TextLayoutData*)m_pLayoutData)->m_pTextLayout;\r
1245         pTextLayout->DoLayout(iBlockIndex, fCalcHeight, fCalcHeight, m_pLayoutData->m_fWidgetHeight - fTopInset);\r
1246         if (fCalcHeight != 0) {\r
1247             if (iBlockIndex == 0) {\r
1248                 fCalcHeight = fCalcHeight + fTopInset;\r
1249             }\r
1250             if (fabs(fHeight - fCalcHeight)  < XFA_FLOAT_PERCISION) {\r
1251                 return FALSE;\r
1252             }\r
1253         }\r
1254         return TRUE;\r
1255     }\r
1256     XFA_ATTRIBUTEENUM iCapPlacement = XFA_ATTRIBUTEENUM_Unknown;\r
1257     FX_FLOAT fCapReserve = 0;\r
1258     if (iBlockIndex == 0) {\r
1259         CXFA_Caption caption = GetCaption();\r
1260         if (caption.IsExistInXML() && caption.GetPresence() != XFA_ATTRIBUTEENUM_Hidden) {\r
1261             iCapPlacement = (XFA_ATTRIBUTEENUM)caption.GetPlacementType();\r
1262             fCapReserve = caption.GetReserve();\r
1263         }\r
1264         if (iCapPlacement == XFA_ATTRIBUTEENUM_Top && fCalcHeight < fCapReserve + fTopInset) {\r
1265             fCalcHeight = 0;\r
1266             return TRUE;\r
1267         }\r
1268         if (iCapPlacement == XFA_ATTRIBUTEENUM_Bottom && m_pLayoutData->m_fWidgetHeight - fCapReserve - fBottomInset) {\r
1269             fCalcHeight = 0;\r
1270             return TRUE;\r
1271         }\r
1272         if (iCapPlacement != XFA_ATTRIBUTEENUM_Top) {\r
1273             fCapReserve = 0;\r
1274         }\r
1275     }\r
1276     FX_INT32 iLinesCount = 0;\r
1277     FX_FLOAT fHeight = m_pLayoutData->m_fWidgetHeight;\r
1278     CFX_WideString wsText;\r
1279     this->GetValue(wsText, XFA_VALUEPICTURE_Display);\r
1280     if (wsText.IsEmpty()) {\r
1281         iLinesCount = 1;\r
1282     } else {\r
1283         if (!((CXFA_FieldLayoutData*)m_pLayoutData)->m_pTextOut) {\r
1284             FX_FLOAT fWidth = 0;\r
1285             GetWidth(fWidth);\r
1286             CalculateAccWidthAndHeight(eUIType, fWidth, fHeight);\r
1287         }\r
1288         iLinesCount = ((CXFA_FieldLayoutData*)m_pLayoutData)->m_pTextOut->GetTotalLines();\r
1289     }\r
1290     if (!((CXFA_FieldLayoutData*)m_pLayoutData)->m_pFieldSplitArray) {\r
1291         ((CXFA_FieldLayoutData*)m_pLayoutData)->m_pFieldSplitArray = FX_NEW CFX_FloatArray;\r
1292     }\r
1293     CFX_FloatArray* pFieldArray = ((CXFA_FieldLayoutData*)m_pLayoutData)->m_pFieldSplitArray;\r
1294     FX_INT32 iFieldSplitCount = pFieldArray->GetSize();\r
1295     for (FX_INT32 i = 0; i < iBlockIndex * 3; i += 3) {\r
1296         iLinesCount -= (FX_INT32)pFieldArray->GetAt(i + 1);\r
1297         fHeight -= pFieldArray->GetAt(i + 2);\r
1298     }\r
1299     if (iLinesCount == 0) {\r
1300         return FALSE;\r
1301     }\r
1302     FX_FLOAT fLineHeight = GetLineHeight();\r
1303     FX_FLOAT fFontSize = GetFontSize();\r
1304     FX_FLOAT fTextHeight = iLinesCount * fLineHeight - fLineHeight + fFontSize;\r
1305     FX_FLOAT fSpaceAbove = 0;\r
1306     FX_FLOAT fStartOffset = 0;\r
1307     if (fHeight > 0.1f && iBlockIndex == 0) {\r
1308         fStartOffset = fTopInset;\r
1309         fHeight -= (fTopInset + fBottomInset);\r
1310         if (CXFA_Para para = this->GetPara()) {\r
1311             fSpaceAbove = para.GetSpaceAbove();\r
1312             FX_FLOAT fSpaceBelow = para.GetSpaceBelow();\r
1313             fHeight -= (fSpaceAbove + fSpaceBelow);\r
1314             switch (para.GetVerticalAlign()) {\r
1315                 case XFA_ATTRIBUTEENUM_Top:\r
1316                     fStartOffset += fSpaceAbove;\r
1317                     break;\r
1318                 case XFA_ATTRIBUTEENUM_Middle:\r
1319                     fStartOffset += ((fHeight - fTextHeight) / 2 + fSpaceAbove);\r
1320                     break;\r
1321                 case XFA_ATTRIBUTEENUM_Bottom:\r
1322                     fStartOffset += (fHeight - fTextHeight + fSpaceAbove);\r
1323                     break;\r
1324             }\r
1325         }\r
1326         if (fStartOffset < 0.1f) {\r
1327             fStartOffset = 0;\r
1328         }\r
1329     }\r
1330     for (FX_INT32 i = iBlockIndex - 1; iBlockIndex > 0 && i < iBlockIndex; i++) {\r
1331         fStartOffset = pFieldArray->GetAt(i * 3) - pFieldArray->GetAt(i * 3 + 2);\r
1332         if (fStartOffset < 0.1f) {\r
1333             fStartOffset = 0;\r
1334         }\r
1335     }\r
1336     if (iFieldSplitCount / 3 == (iBlockIndex + 1)) {\r
1337         pFieldArray->SetAt(0, fStartOffset);\r
1338     } else {\r
1339         pFieldArray->Add(fStartOffset);\r
1340     }\r
1341     XFA_VERSION version = GetDoc()->GetXFADoc()->GetCurVersionMode();\r
1342     FX_BOOL bCanSplitNoContent = FALSE;\r
1343     XFA_ATTRIBUTEENUM eLayoutMode;\r
1344     this->GetNode()->GetNodeItem(XFA_NODEITEM_Parent)->TryEnum(XFA_ATTRIBUTE_Layout, eLayoutMode, TRUE);\r
1345     if ((eLayoutMode == XFA_ATTRIBUTEENUM_Position || eLayoutMode == XFA_ATTRIBUTEENUM_Tb || eLayoutMode == XFA_ATTRIBUTEENUM_Row || eLayoutMode == XFA_ATTRIBUTEENUM_Table) && version > XFA_VERSION_208) {\r
1346         bCanSplitNoContent = TRUE;\r
1347     }\r
1348     if ((eLayoutMode == XFA_ATTRIBUTEENUM_Tb || eLayoutMode == XFA_ATTRIBUTEENUM_Row || eLayoutMode == XFA_ATTRIBUTEENUM_Table) && version <= XFA_VERSION_208) {\r
1349         if (fStartOffset < fCalcHeight) {\r
1350             bCanSplitNoContent = TRUE;\r
1351         } else {\r
1352             fCalcHeight = 0;\r
1353             return TRUE;\r
1354         }\r
1355     }\r
1356     if (bCanSplitNoContent) {\r
1357         if ((fCalcHeight - fTopInset - fSpaceAbove < fLineHeight)) {\r
1358             fCalcHeight = 0;\r
1359             return TRUE;\r
1360         }\r
1361         if (fStartOffset + XFA_FLOAT_PERCISION >= fCalcHeight) {\r
1362             if (iFieldSplitCount / 3 == (iBlockIndex + 1)) {\r
1363                 pFieldArray->SetAt(iBlockIndex * 3 + 1, 0);\r
1364                 pFieldArray->SetAt(iBlockIndex * 3 + 2, fCalcHeight);\r
1365             } else {\r
1366                 pFieldArray->Add(0);\r
1367                 pFieldArray->Add(fCalcHeight);\r
1368             }\r
1369             return FALSE;\r
1370         }\r
1371         if (fCalcHeight - fStartOffset < fLineHeight) {\r
1372             fCalcHeight = fStartOffset;\r
1373             if (iFieldSplitCount / 3 == (iBlockIndex + 1)) {\r
1374                 pFieldArray->SetAt(iBlockIndex * 3 + 1, 0);\r
1375                 pFieldArray->SetAt(iBlockIndex * 3 + 2, fCalcHeight);\r
1376             } else {\r
1377                 pFieldArray->Add(0);\r
1378                 pFieldArray->Add(fCalcHeight);\r
1379             }\r
1380             return TRUE;\r
1381         }\r
1382         FX_FLOAT fTextNum = fCalcHeight + XFA_FLOAT_PERCISION - fCapReserve - fStartOffset;\r
1383         FX_INT32 iLineNum = (FX_INT32)((fTextNum + (fLineHeight - fFontSize)) / fLineHeight);\r
1384         if (iLineNum >= iLinesCount) {\r
1385             if (fCalcHeight - fStartOffset - fTextHeight >= fFontSize) {\r
1386                 if (iFieldSplitCount / 3 == (iBlockIndex + 1)) {\r
1387                     pFieldArray->SetAt(iBlockIndex * 3 + 1, (FX_FLOAT)iLinesCount);\r
1388                     pFieldArray->SetAt(iBlockIndex * 3 + 2, fCalcHeight);\r
1389                 } else {\r
1390                     pFieldArray->Add((FX_FLOAT)iLinesCount);\r
1391                     pFieldArray->Add(fCalcHeight);\r
1392                 }\r
1393                 return FALSE;\r
1394             }\r
1395             if (fHeight - fStartOffset - fTextHeight < fFontSize) {\r
1396                 iLineNum -= 1;\r
1397                 if (iLineNum == 0) {\r
1398                     fCalcHeight = 0;\r
1399                     return TRUE;\r
1400                 }\r
1401             } else {\r
1402                 iLineNum = (FX_INT32)(fTextNum / fLineHeight);\r
1403             }\r
1404         }\r
1405         if (iLineNum > 0) {\r
1406             FX_FLOAT fSplitHeight = iLineNum * fLineHeight  + fCapReserve + fStartOffset;\r
1407             if (iFieldSplitCount / 3 == (iBlockIndex + 1)) {\r
1408                 pFieldArray->SetAt(iBlockIndex * 3 + 1, (FX_FLOAT)iLineNum);\r
1409                 pFieldArray->SetAt(iBlockIndex * 3 + 2, fSplitHeight);\r
1410             } else {\r
1411                 pFieldArray->Add((FX_FLOAT)iLineNum);\r
1412                 pFieldArray->Add(fSplitHeight);\r
1413             }\r
1414             if (fabs(fSplitHeight - fCalcHeight)  < XFA_FLOAT_PERCISION) {\r
1415                 return FALSE;\r
1416             }\r
1417             fCalcHeight = fSplitHeight;\r
1418             return TRUE;\r
1419         }\r
1420     }\r
1421     fCalcHeight = 0;\r
1422     return TRUE;\r
1423 }\r
1424 void CXFA_WidgetAcc::InitLayoutData()\r
1425 {\r
1426     if (m_pLayoutData) {\r
1427         return;\r
1428     }\r
1429     switch (GetUIType()) {\r
1430         case XFA_ELEMENT_Text:\r
1431             m_pLayoutData = FX_NEW CXFA_TextLayoutData;\r
1432             return;\r
1433         case XFA_ELEMENT_TextEdit:\r
1434             m_pLayoutData = FX_NEW CXFA_TextEditData;\r
1435             return;\r
1436         case XFA_ELEMENT_Image:\r
1437             m_pLayoutData = FX_NEW CXFA_ImageLayoutData;\r
1438             return;\r
1439         case XFA_ELEMENT_ImageEdit:\r
1440             m_pLayoutData = FX_NEW CXFA_ImageEditData;\r
1441             return;\r
1442         default:\r
1443             break;\r
1444     }\r
1445     if (GetClassID() == XFA_ELEMENT_Field) {\r
1446         m_pLayoutData = FX_NEW CXFA_FieldLayoutData;\r
1447     } else {\r
1448         m_pLayoutData = FX_NEW CXFA_WidgetLayoutData;\r
1449     }\r
1450 }\r
1451 void CXFA_WidgetAcc::StartTextLayout(FX_FLOAT& fCalcWidth, FX_FLOAT& fCalcHeight)\r
1452 {\r
1453     LoadText();\r
1454     CXFA_TextLayout* pTextLayout = ((CXFA_TextLayoutData*)m_pLayoutData)->m_pTextLayout;\r
1455     FX_FLOAT fTextHeight = 0;\r
1456     if (fCalcWidth > 0 && fCalcHeight > 0) {\r
1457         FX_FLOAT fWidth = GetWidthWithoutMargin(fCalcWidth);\r
1458         pTextLayout->StartLayout(fWidth);\r
1459         fTextHeight = fCalcHeight;\r
1460         fTextHeight = GetHeightWithoutMargin(fTextHeight);\r
1461         pTextLayout->DoLayout(0, fTextHeight, -1, fTextHeight);\r
1462         return;\r
1463     }\r
1464     if (fCalcWidth > 0 && fCalcHeight < 0) {\r
1465         FX_FLOAT fWidth = GetWidthWithoutMargin(fCalcWidth);\r
1466         pTextLayout->StartLayout(fWidth);\r
1467     }\r
1468     if (fCalcWidth < 0 && fCalcHeight < 0) {\r
1469         FX_FLOAT fMaxWidth = -1;\r
1470         FX_BOOL bRet = GetWidth(fMaxWidth);\r
1471         if (bRet) {\r
1472             FX_FLOAT fWidth = GetWidthWithoutMargin(fMaxWidth);\r
1473             pTextLayout->StartLayout(fWidth);\r
1474         } else {\r
1475             FX_FLOAT fWidth = pTextLayout->StartLayout(fMaxWidth);\r
1476             fMaxWidth = CalculateWidgetAutoWidth(fWidth);\r
1477             fWidth = GetWidthWithoutMargin(fMaxWidth);\r
1478             pTextLayout->StartLayout(fWidth);\r
1479         }\r
1480         fCalcWidth = fMaxWidth;\r
1481     }\r
1482     if (m_pLayoutData->m_fWidgetHeight < 0) {\r
1483         m_pLayoutData->m_fWidgetHeight = pTextLayout->GetLayoutHeight();\r
1484         m_pLayoutData->m_fWidgetHeight = CalculateWidgetAutoHeight(m_pLayoutData->m_fWidgetHeight);\r
1485     }\r
1486     fTextHeight = m_pLayoutData->m_fWidgetHeight;\r
1487     fTextHeight = GetHeightWithoutMargin(fTextHeight);\r
1488     pTextLayout->DoLayout(0, fTextHeight, -1, fTextHeight);\r
1489     fCalcHeight = m_pLayoutData->m_fWidgetHeight;\r
1490 }\r
1491 FX_BOOL CXFA_WidgetAcc::LoadCaption()\r
1492 {\r
1493     InitLayoutData();\r
1494     return ((CXFA_FieldLayoutData*)m_pLayoutData)->LoadCaption(this);\r
1495 }\r
1496 CXFA_TextLayout* CXFA_WidgetAcc::GetCaptionTextLayout()\r
1497 {\r
1498     return m_pLayoutData ? ((CXFA_FieldLayoutData*)m_pLayoutData)->m_pCapTextLayout : NULL;\r
1499 }\r
1500 CXFA_TextLayout* CXFA_WidgetAcc::GetTextLayout()\r
1501 {\r
1502     return m_pLayoutData ? ((CXFA_TextLayoutData*)m_pLayoutData)->m_pTextLayout : NULL;\r
1503 }\r
1504 CFX_DIBitmap* CXFA_WidgetAcc::GetImageImage()\r
1505 {\r
1506     return m_pLayoutData ? ((CXFA_ImageLayoutData*)m_pLayoutData)->m_pDIBitmap : NULL;\r
1507 }\r
1508 CFX_DIBitmap* CXFA_WidgetAcc::GetImageEditImage()\r
1509 {\r
1510     return m_pLayoutData ? ((CXFA_ImageEditData*)m_pLayoutData)->m_pDIBitmap : NULL;\r
1511 }\r
1512 void CXFA_WidgetAcc::SetImageImage(CFX_DIBitmap* newImage)\r
1513 {\r
1514     if(((CXFA_ImageLayoutData*)m_pLayoutData)->m_pDIBitmap == newImage) {\r
1515         return;\r
1516     }\r
1517     if(((CXFA_ImageLayoutData*)m_pLayoutData)->m_pDIBitmap && !((CXFA_ImageLayoutData*)m_pLayoutData)->m_bNamedImage) {\r
1518         delete ((CXFA_ImageLayoutData*)m_pLayoutData)->m_pDIBitmap;\r
1519         ((CXFA_ImageLayoutData*)m_pLayoutData)->m_pDIBitmap = NULL;\r
1520     }\r
1521     ((CXFA_ImageLayoutData*)m_pLayoutData)->m_pDIBitmap = newImage;\r
1522 }\r
1523 void CXFA_WidgetAcc::SetImageEditImage(CFX_DIBitmap* newImage)\r
1524 {\r
1525     if(((CXFA_ImageEditData*)m_pLayoutData)->m_pDIBitmap == newImage) {\r
1526         return;\r
1527     }\r
1528     if(((CXFA_ImageEditData*)m_pLayoutData)->m_pDIBitmap && !((CXFA_ImageEditData*)m_pLayoutData)->m_bNamedImage) {\r
1529         delete ((CXFA_ImageEditData*)m_pLayoutData)->m_pDIBitmap;\r
1530         ((CXFA_ImageEditData*)m_pLayoutData)->m_pDIBitmap = NULL;\r
1531     }\r
1532     ((CXFA_ImageEditData*)m_pLayoutData)->m_pDIBitmap = newImage;\r
1533 }\r
1534 CXFA_WidgetLayoutData* CXFA_WidgetAcc::GetWidgetLayoutData()\r
1535 {\r
1536     return m_pLayoutData;\r
1537 }\r
1538 IFX_Font* CXFA_WidgetAcc::GetFDEFont()\r
1539 {\r
1540     CFX_WideStringC wsFontName = FX_WSTRC(L"Courier");\r
1541     FX_DWORD dwFontStyle = 0;\r
1542     if (CXFA_Font font = this->GetFont()) {\r
1543         if (font.IsBold()) {\r
1544             dwFontStyle |= FX_FONTSTYLE_Bold;\r
1545         }\r
1546         if (font.IsItalic()) {\r
1547             dwFontStyle |= FX_FONTSTYLE_Italic;\r
1548         }\r
1549         font.GetTypeface(wsFontName);\r
1550     }\r
1551     CXFA_FFDoc* pDoc = GetDoc();\r
1552     return pDoc->GetApp()->GetXFAFontMgr()->GetFont((XFA_HDOC)pDoc, wsFontName, dwFontStyle);\r
1553 }\r
1554 FX_FLOAT CXFA_WidgetAcc::GetFontSize()\r
1555 {\r
1556     FX_FLOAT fFontSize = 10.0f;\r
1557     if (CXFA_Font font = this->GetFont()) {\r
1558         fFontSize = font.GetFontSize();\r
1559     }\r
1560     return fFontSize < 0.1f ? 10.0f : fFontSize;\r
1561 }\r
1562 FX_FLOAT CXFA_WidgetAcc::GetLineHeight()\r
1563 {\r
1564     FX_FLOAT fLineHeight = 0;\r
1565     if (CXFA_Para para = this->GetPara()) {\r
1566         fLineHeight = para.GetLineHeight();\r
1567     }\r
1568     if (fLineHeight < 1) {\r
1569         fLineHeight = GetFontSize() * 1.2f;\r
1570     }\r
1571     return fLineHeight;\r
1572 }\r
1573 FX_ARGB CXFA_WidgetAcc::GetTextColor()\r
1574 {\r
1575     if (CXFA_Font font = this->GetFont()) {\r
1576         return font.GetColor();\r
1577     }\r
1578     return 0xFF000000;\r
1579 }\r
1580 CXFA_Node* CXFA_TextProvider::GetTextNode(FX_BOOL &bRichText)\r
1581 {\r
1582     bRichText = FALSE;\r
1583     if (m_pTextNode) {\r
1584         if (m_pTextNode->GetClassID() == XFA_ELEMENT_ExData) {\r
1585             CFX_WideString wsContentType;\r
1586             m_pTextNode->GetAttribute(XFA_ATTRIBUTE_ContentType, wsContentType, FALSE);\r
1587             if (wsContentType.Equal(FX_WSTRC(L"text/html"))) {\r
1588                 bRichText = TRUE;\r
1589             }\r
1590         }\r
1591         return m_pTextNode;\r
1592     }\r
1593     if (m_eType == XFA_TEXTPROVIDERTYPE_Text) {\r
1594         CXFA_Node* pElementNode = m_pWidgetAcc->GetNode();\r
1595         CXFA_Node *pValueNode = pElementNode->GetChild(0, XFA_ELEMENT_Value);\r
1596         if (!pValueNode) {\r
1597             return NULL;\r
1598         }\r
1599         CXFA_Node *pChildNode = pValueNode->GetNodeItem(XFA_NODEITEM_FirstChild);\r
1600         if (pChildNode && pChildNode->GetClassID() == XFA_ELEMENT_ExData) {\r
1601             CFX_WideString wsContentType;\r
1602             pChildNode->GetAttribute(XFA_ATTRIBUTE_ContentType, wsContentType, FALSE);\r
1603             if (wsContentType.Equal(FX_WSTRC(L"text/html"))) {\r
1604                 bRichText = TRUE;\r
1605             }\r
1606         }\r
1607         return pChildNode;\r
1608     } else if (m_eType == XFA_TEXTPROVIDERTYPE_Datasets) {\r
1609         CXFA_Node* pBind = m_pWidgetAcc->GetDatasets();\r
1610         IFDE_XMLNode *pXMLNode = pBind->GetXMLMappingNode();\r
1611         FXSYS_assert(pXMLNode);\r
1612         for(IFDE_XMLNode *pXMLChild = pXMLNode->GetNodeItem(IFDE_XMLNode::FirstChild); pXMLChild; pXMLChild = pXMLChild->GetNodeItem(IFDE_XMLNode::NextSibling)) {\r
1613             if (pXMLChild->GetType() == FDE_XMLNODE_Element) {\r
1614                 IFDE_XMLElement *pElement = (IFDE_XMLElement *)pXMLChild;\r
1615                 if(XFA_RecognizeRichText(pElement)) {\r
1616                     bRichText = TRUE;\r
1617                 }\r
1618             }\r
1619         }\r
1620         return pBind;\r
1621     } else if (m_eType == XFA_TEXTPROVIDERTYPE_Caption) {\r
1622         CXFA_Node *pCaptionNode = m_pWidgetAcc->GetNode()->GetChild(0, XFA_ELEMENT_Caption);\r
1623         if (pCaptionNode == NULL) {\r
1624             return NULL;\r
1625         }\r
1626         CXFA_Node *pValueNode = pCaptionNode->GetChild(0, XFA_ELEMENT_Value);\r
1627         if (pValueNode == NULL) {\r
1628             return NULL;\r
1629         }\r
1630         CXFA_Node *pChildNode = pValueNode->GetNodeItem(XFA_NODEITEM_FirstChild);\r
1631         if (pChildNode && pChildNode->GetClassID() == XFA_ELEMENT_ExData) {\r
1632             CFX_WideString wsContentType;\r
1633             pChildNode->GetAttribute(XFA_ATTRIBUTE_ContentType, wsContentType, FALSE);\r
1634             if (wsContentType.Equal(FX_WSTRC(L"text/html"))) {\r
1635                 bRichText = TRUE;\r
1636             }\r
1637         }\r
1638         return pChildNode;\r
1639     }\r
1640     CXFA_Node *pItemNode = m_pWidgetAcc->GetNode()->GetChild(0, XFA_ELEMENT_Items);\r
1641     if (pItemNode == NULL) {\r
1642         return NULL;\r
1643     }\r
1644     CXFA_Node* pNode = pItemNode->GetNodeItem(XFA_NODEITEM_FirstChild);\r
1645     while(pNode) {\r
1646         CFX_WideStringC wsName;\r
1647         pNode->TryCData(XFA_ATTRIBUTE_Name, wsName);\r
1648         if (m_eType == XFA_TEXTPROVIDERTYPE_Rollover && wsName == FX_WSTRC(L"rollover")) {\r
1649             return pNode;\r
1650         }\r
1651         if (m_eType == XFA_TEXTPROVIDERTYPE_Down && wsName == FX_WSTRC(L"down")) {\r
1652             return pNode;\r
1653         }\r
1654         pNode = pNode->GetNodeItem(XFA_NODEITEM_NextSibling);\r
1655     }\r
1656     return NULL;\r
1657 }\r
1658 CXFA_Para CXFA_TextProvider::GetParaNode()\r
1659 {\r
1660     if (m_eType == XFA_TEXTPROVIDERTYPE_Text) {\r
1661         return m_pWidgetAcc->GetPara();\r
1662     }\r
1663     CXFA_Node *pNode = m_pWidgetAcc->GetNode()->GetChild(0, XFA_ELEMENT_Caption);\r
1664     return pNode->GetChild(0, XFA_ELEMENT_Para);\r
1665 }\r
1666 CXFA_Font CXFA_TextProvider::GetFontNode()\r
1667 {\r
1668     if (m_eType == XFA_TEXTPROVIDERTYPE_Text) {\r
1669         return m_pWidgetAcc->GetFont();\r
1670     }\r
1671     CXFA_Node *pNode = m_pWidgetAcc->GetNode()->GetChild(0, XFA_ELEMENT_Caption);\r
1672     pNode = pNode->GetChild(0, XFA_ELEMENT_Font);\r
1673     if (pNode) {\r
1674         return pNode;\r
1675     }\r
1676     return m_pWidgetAcc->GetFont();\r
1677 }\r
1678 FX_BOOL CXFA_TextProvider::IsCheckButtonAndAutoWidth()\r
1679 {\r
1680     XFA_ELEMENT eType = m_pWidgetAcc->GetUIType();\r
1681     if (eType == XFA_ELEMENT_CheckButton) {\r
1682         FX_FLOAT fWidth = 0;\r
1683         return !m_pWidgetAcc->GetWidth(fWidth);\r
1684     }\r
1685     return FALSE;\r
1686 }\r
1687 FX_BOOL CXFA_TextProvider::GetEmbbedObj(FX_BOOL bURI, FX_BOOL bRaw, const CFX_WideString &wsAttr, CFX_WideString &wsValue)\r
1688 {\r
1689     if (m_eType != XFA_TEXTPROVIDERTYPE_Text) {\r
1690         return FALSE;\r
1691     }\r
1692     if (bURI) {\r
1693         CXFA_Node* pWidgetNode = m_pWidgetAcc->GetNode();\r
1694         CXFA_Node* pParent = pWidgetNode->GetNodeItem(XFA_NODEITEM_Parent);\r
1695         CXFA_Document* pDocument = pWidgetNode->GetDocument();\r
1696         CXFA_Node* pIDNode = NULL;\r
1697         CXFA_WidgetAcc* pEmbAcc = NULL;\r
1698         if (pParent) {\r
1699             pIDNode = pDocument->GetNodeByID(pParent, wsAttr);\r
1700         }\r
1701         if (!pIDNode) {\r
1702             pIDNode = pDocument->GetNodeByID((CXFA_Node*)pDocument->GetXFANode(XFA_HASHCODE_Form), wsAttr);\r
1703         }\r
1704         if (pIDNode) {\r
1705             pEmbAcc = (CXFA_WidgetAcc*)pIDNode->GetWidgetData();\r
1706         }\r
1707         if (pEmbAcc) {\r
1708             pEmbAcc->GetValue(wsValue, XFA_VALUEPICTURE_Display);\r
1709             return TRUE;\r
1710         }\r
1711     }\r
1712     return FALSE;\r
1713 }\r