Restore logic of CreateChildUIAndValueNodesIfNeeded().
CreateUIChild() was changed and renamed to
CreateChildUIAndValueNodesIfNeeded() in:
https://pdfium-review.googlesource.com/c/pdfium/+/24390
This caused some bugs but it's too far back for a rollback.
This cl restores the logic of CreateUIChild() keeping the new
signature.
Bug: chromium:838994
Change-Id: I44ce741fdb90f8b0fd11379b5e881e376c307f0c
Reviewed-on: https://pdfium-review.googlesource.com/32090
Reviewed-by: dsinclair <dsinclair@chromium.org>
Commit-Queue: Henrique Nakashima <hnakashima@chromium.org>
diff --git a/testing/resources/pixel/xfa_specific/xfa_rectangle_node.in b/testing/resources/pixel/xfa_specific/xfa_rectangle_node.in
new file mode 100644
index 0000000..c2f7875
--- /dev/null
+++ b/testing/resources/pixel/xfa_specific/xfa_rectangle_node.in
@@ -0,0 +1,77 @@
+{{header}}
+
+%% Original object ID: 24 0
+{{object 1 0}}
+<<
+  /AcroForm 2 0 R
+  /Extensions <<
+    /ADBE <<
+      /BaseVersion /1.7
+      /ExtensionLevel 8
+    >>
+  >>
+  /NeedsRendering true
+  /Type /Catalog
+>>
+endobj
+
+%% Original object ID: 32 0
+{{object 2 0}}
+<<
+  /XFA [
+    (preamble)
+    3 0 R
+    (config)
+    4 0 R
+    (template)
+    5 0 R
+    (localeSet)
+    6 0 R
+    (postamble)
+    7 0 R
+  ]
+>>
+endobj
+
+{{xfapreamble 3 0}}
+{{xfaconfig 4 0}}
+
+{{object 5 0}}
+<<
+  {{streamlen}}
+>>
+stream
+<template xmlns="http://www.xfa.org/schema/xfa-template/3.3/">
+  <subform name="form1" layout="tb" locale="en_US" restoreState="auto">
+    <pageSet>
+      <pageArea name="Page1" id="Page1">
+        <contentArea x="18pt" y="18pt" w="612pt" h="792pt"/>
+        <medium stock="default" short="612pt" long="792pt"/>
+      </pageArea>
+    </pageSet>
+    <subform w="576pt" h="756pt" name="Page1">
+      <draw h="11.43mm" name="Rectangle3" w="30.48mm" x="170.18mm" y="65.868mm">
+        <ui>
+          <defaultUi />
+        </ui>
+        <value>
+          <rectangle>
+            <corner radius="5.08mm" />
+            <edge />
+          </rectangle>
+        </value>
+      </draw>
+    </subform>
+  </subform>
+</template>
+endstream
+endobj
+
+{{xfalocale 6 0}}
+
+{{xfapostamble 7 0}}
+
+{{xref}}
+{{trailer}}
+{{startxref}}
+%%EOF
diff --git a/testing/resources/pixel/xfa_specific/xfa_rectangle_node_expected.pdf.0.png b/testing/resources/pixel/xfa_specific/xfa_rectangle_node_expected.pdf.0.png
new file mode 100644
index 0000000..a7eb49e
--- /dev/null
+++ b/testing/resources/pixel/xfa_specific/xfa_rectangle_node_expected.pdf.0.png
Binary files differ
diff --git a/xfa/fxfa/parser/cxfa_node.cpp b/xfa/fxfa/parser/cxfa_node.cpp
index e2bde5c..91e78dc 100644
--- a/xfa/fxfa/parser/cxfa_node.cpp
+++ b/xfa/fxfa/parser/cxfa_node.cpp
@@ -2355,10 +2355,8 @@
     }
   }
 
-  XFA_FFWidgetType ff_widget_type =
-      pUIChild ? pUIChild->GetDefaultFFWidgetType() : XFA_FFWidgetType::kNone;
-  XFA_Element ui_child_type =
-      pUIChild ? pUIChild->GetElementType() : XFA_Element::Unknown;
+  XFA_FFWidgetType widget_type = XFA_FFWidgetType::kNone;
+  XFA_Element expected_ui_child_type = XFA_Element::Unknown;
 
   // Both Field and Draw nodes have a Value child. So, we should either always
   // have it, or always create it. If we don't get the Value child for some
@@ -2371,82 +2369,77 @@
   // that child must be the type we want to use.
   CXFA_Node* child = value->GetFirstChild();
   if (child) {
-    XFA_FFWidgetType tmp_widget_type = XFA_FFWidgetType::kNone;
     switch (child->GetElementType()) {
       case XFA_Element::Boolean:
-        ui_child_type = XFA_Element::CheckButton;
-        tmp_widget_type = XFA_FFWidgetType::kCheckButton;
+        expected_ui_child_type = XFA_Element::CheckButton;
         break;
       case XFA_Element::Integer:
       case XFA_Element::Decimal:
       case XFA_Element::Float:
-        ui_child_type = XFA_Element::NumericEdit;
-        tmp_widget_type = XFA_FFWidgetType::kNumericEdit;
+        expected_ui_child_type = XFA_Element::NumericEdit;
         break;
       case XFA_Element::ExData:
       case XFA_Element::Text:
-        ui_child_type = XFA_Element::TextEdit;
-        tmp_widget_type = XFA_FFWidgetType::kTextEdit;
+        expected_ui_child_type = XFA_Element::TextEdit;
+        widget_type = XFA_FFWidgetType::kText;
         break;
       case XFA_Element::Date:
       case XFA_Element::Time:
       case XFA_Element::DateTime:
-        ui_child_type = XFA_Element::DateTimeEdit;
-        tmp_widget_type = XFA_FFWidgetType::kDateTimeEdit;
+        expected_ui_child_type = XFA_Element::DateTimeEdit;
         break;
       case XFA_Element::Image:
-        ui_child_type = XFA_Element::ImageEdit;
-        tmp_widget_type = XFA_FFWidgetType::kImageEdit;
+        expected_ui_child_type = XFA_Element::ImageEdit;
+        widget_type = XFA_FFWidgetType::kImage;
         break;
       case XFA_Element::Arc:
-        ui_child_type = XFA_Element::DefaultUi;
-        tmp_widget_type = XFA_FFWidgetType::kArc;
+        expected_ui_child_type = XFA_Element::DefaultUi;
+        widget_type = XFA_FFWidgetType::kArc;
         break;
       case XFA_Element::Line:
-        ui_child_type = XFA_Element::DefaultUi;
-        tmp_widget_type = XFA_FFWidgetType::kLine;
+        expected_ui_child_type = XFA_Element::DefaultUi;
+        widget_type = XFA_FFWidgetType::kLine;
         break;
       case XFA_Element::Rectangle:
-        ui_child_type = XFA_Element::DefaultUi;
-        tmp_widget_type = XFA_FFWidgetType::kRectangle;
+        expected_ui_child_type = XFA_Element::DefaultUi;
+        widget_type = XFA_FFWidgetType::kRectangle;
         break;
       default:
         NOTREACHED();
         break;
     }
+  }
 
-    // Only set the FFWidget if we didn't already set it from the UI child.
-    if (ff_widget_type == XFA_FFWidgetType::kNone)
-      ff_widget_type = tmp_widget_type;
+  if (eType == XFA_Element::Draw) {
+    if (pUIChild && pUIChild->GetElementType() == XFA_Element::TextEdit) {
+      widget_type = XFA_FFWidgetType::kText;
+    } else if (pUIChild &&
+               pUIChild->GetElementType() == XFA_Element::ImageEdit) {
+      widget_type = XFA_FFWidgetType::kImage;
+    } else if (widget_type == XFA_FFWidgetType::kNone) {
+      widget_type = XFA_FFWidgetType::kText;
+    }
+  } else if (eType == XFA_Element::Field) {
+    if (pUIChild && pUIChild->GetElementType() == XFA_Element::DefaultUi) {
+      widget_type = XFA_FFWidgetType::kTextEdit;
+    } else if (pUIChild) {
+      widget_type = pUIChild->GetDefaultFFWidgetType();
+    } else if (expected_ui_child_type == XFA_Element::Unknown) {
+      widget_type = XFA_FFWidgetType::kTextEdit;
+    }
+  } else {
+    NOTREACHED();
   }
 
   if (!pUIChild) {
-    if (ui_child_type == XFA_Element::Unknown)
-      ui_child_type = XFA_Element::TextEdit;
-
-    pUIChild = CreateUINodeIfNeeded(pUI, ui_child_type);
-    if (ff_widget_type == XFA_FFWidgetType::kNone)
-      ff_widget_type = pUIChild->GetDefaultFFWidgetType();
+    if (expected_ui_child_type == XFA_Element::Unknown)
+      expected_ui_child_type = XFA_Element::TextEdit;
+    pUIChild = pUI->JSObject()->GetOrCreateProperty<CXFA_Node>(
+        0, expected_ui_child_type);
   }
 
-  // When handling draw children, change the image and text edit items to
-  // be non-edit.
-  if (eType == XFA_Element::Draw) {
-    switch (pUIChild->GetElementType()) {
-      case XFA_Element::TextEdit:
-        ff_widget_type = XFA_FFWidgetType::kText;
-        break;
-      case XFA_Element::ImageEdit:
-        ff_widget_type = XFA_FFWidgetType::kImage;
-        break;
-      default:
-        break;
-    }
-  }
-  ASSERT(ff_widget_type != XFA_FFWidgetType::kNone);
-
   CreateValueNodeIfNeeded(value, pUIChild);
-  return {ff_widget_type, pUI};
+  return {widget_type, pUI};
 }
 
 XFA_FFWidgetType CXFA_Node::GetDefaultFFWidgetType() const {