Add test for FX_DATETIMETYPE_DateTime formatting.

Precursor to fixing some issues in time formatting.

This case was formerly not covered by its own tests. Also make dispatch
saner so that it doesn't rely on some artifact of bit patterns within
the enum value.

Change-Id: I08207a7cde6d5f2784ff2171a15c5d427735030d
Reviewed-on: https://pdfium-review.googlesource.com/c/pdfium/+/52171
Reviewed-by: Lei Zhang <thestig@chromium.org>
Commit-Queue: Tom Sepez <tsepez@chromium.org>
diff --git a/xfa/fgas/crt/cfgas_stringformatter.cpp b/xfa/fgas/crt/cfgas_stringformatter.cpp
index 60b8c46..fca1971 100644
--- a/xfa/fgas/crt/cfgas_stringformatter.cpp
+++ b/xfa/fgas/crt/cfgas_stringformatter.cpp
@@ -1672,41 +1672,39 @@
   if (wsSrcDateTime.IsEmpty() || m_spPattern.empty())
     return false;
 
+  LocaleIface* pLocale = nullptr;
   WideString wsDatePattern;
   WideString wsTimePattern;
-  LocaleIface* pLocale = nullptr;
   FX_DATETIMETYPE eCategory =
       GetDateTimeFormat(&pLocale, &wsDatePattern, &wsTimePattern);
   if (!pLocale)
     return false;
+
   if (eCategory == FX_DATETIMETYPE_Unknown)
     eCategory = eDateTimeType;
-  if (eCategory == FX_DATETIMETYPE_Unknown)
-    return false;
-  if (eCategory == FX_DATETIMETYPE_TimeDate) {
-    size_t iStart = 0;
-    if (!ParseLocaleTime(wsSrcDateTime, wsTimePattern, pLocale, dtValue,
-                         &iStart)) {
+
+  size_t iStart = 0;
+  switch (eCategory) {
+    case FX_DATETIMETYPE_Date:
+      return ParseLocaleDate(wsSrcDateTime, wsDatePattern, pLocale, dtValue,
+                             &iStart);
+    case FX_DATETIMETYPE_Time:
+      return ParseLocaleTime(wsSrcDateTime, wsTimePattern, pLocale, dtValue,
+                             &iStart);
+    case FX_DATETIMETYPE_DateTime:
+      return ParseLocaleDate(wsSrcDateTime, wsTimePattern, pLocale, dtValue,
+                             &iStart) &&
+             ParseLocaleTime(wsSrcDateTime, wsDatePattern, pLocale, dtValue,
+                             &iStart);
+    case FX_DATETIMETYPE_TimeDate:
+      return ParseLocaleTime(wsSrcDateTime, wsTimePattern, pLocale, dtValue,
+                             &iStart) &&
+             ParseLocaleDate(wsSrcDateTime, wsDatePattern, pLocale, dtValue,
+                             &iStart);
+    case FX_DATETIMETYPE_Unknown:
+    default:
       return false;
-    }
-    if (!ParseLocaleDate(wsSrcDateTime, wsDatePattern, pLocale, dtValue,
-                         &iStart)) {
-      return false;
-    }
-  } else {
-    size_t iStart = 0;
-    if ((eCategory & FX_DATETIMETYPE_Date) &&
-        !ParseLocaleDate(wsSrcDateTime, wsDatePattern, pLocale, dtValue,
-                         &iStart)) {
-      return false;
-    }
-    if ((eCategory & FX_DATETIMETYPE_Time) &&
-        !ParseLocaleTime(wsSrcDateTime, wsTimePattern, pLocale, dtValue,
-                         &iStart)) {
-      return false;
-    }
   }
-  return true;
 }
 
 bool CFGAS_StringFormatter::ParseZero(const WideString& wsSrcText) const {
diff --git a/xfa/fgas/crt/cfgas_stringformatter_unittest.cpp b/xfa/fgas/crt/cfgas_stringformatter_unittest.cpp
index 4cf91c2..64e7d8a 100644
--- a/xfa/fgas/crt/cfgas_stringformatter_unittest.cpp
+++ b/xfa/fgas/crt/cfgas_stringformatter_unittest.cpp
@@ -194,6 +194,34 @@
   for (size_t i = 0; i < FX_ArraySize(tests); ++i) {
     WideString result;
     EXPECT_TRUE(fmt(tests[i].locale, tests[i].pattern)
+                    ->FormatDateTime(tests[i].input, FX_DATETIMETYPE_DateTime,
+                                     &result));
+    EXPECT_STREQ(tests[i].output, result.c_str()) << " TEST: " << i;
+  }
+}
+
+TEST_F(CFGAS_StringFormatterTest, TimeDateFormat) {
+  struct {
+    const wchar_t* locale;
+    const wchar_t* input;
+    const wchar_t* pattern;
+    const wchar_t* output;
+  } tests[] = {
+      {L"en", L"1999-07-16T10:30Z",
+       L"'At' time{HH:MM Z} 'on' date{MMM DD, YYYY}",
+       L"At 10:30 GMT on Jul 16, 1999"},
+      {L"en", L"1999-07-16T10:30", L"'At' time{HH:MM} 'on' date{MMM DD, YYYY}",
+       L"At 10:30 on Jul 16, 1999"},
+      {L"en", L"1999-07-16T10:30Z",
+       L"time{'At' HH:MM Z} date{'on' MMM DD, YYYY}",
+       L"At 10:30 GMT on Jul 16, 1999"},
+      {L"en", L"1999-07-16T10:30Z",
+       L"time{'At 'HH:MM Z}date{' on 'MMM DD, YYYY}",
+       L"At 10:30 GMT on Jul 16, 1999"}};
+
+  for (size_t i = 0; i < FX_ArraySize(tests); ++i) {
+    WideString result;
+    EXPECT_TRUE(fmt(tests[i].locale, tests[i].pattern)
                     ->FormatDateTime(tests[i].input, FX_DATETIMETYPE_TimeDate,
                                      &result));
     EXPECT_STREQ(tests[i].output, result.c_str()) << " TEST: " << i;