Upload upstream chromium 67.0.3396
[platform/framework/web/chromium-efl.git] / base / i18n / bidi_line_iterator_unittest.cc
1 // Copyright 2017 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "base/i18n/bidi_line_iterator.h"
6
7 #include "base/macros.h"
8 #include "base/strings/utf_string_conversions.h"
9 #include "testing/gtest/include/gtest/gtest.h"
10
11 namespace base {
12 namespace i18n {
13 namespace {
14
15 class BiDiLineIteratorTest : public testing::TestWithParam<TextDirection> {
16  public:
17   BiDiLineIteratorTest() = default;
18
19   BiDiLineIterator* iterator() { return &iterator_; }
20
21  private:
22   BiDiLineIterator iterator_;
23
24   DISALLOW_COPY_AND_ASSIGN(BiDiLineIteratorTest);
25 };
26
27 TEST_P(BiDiLineIteratorTest, OnlyLTR) {
28   iterator()->Open(UTF8ToUTF16("abc 馃榿 娴嬭瘯"), GetParam(),
29                    BiDiLineIterator::CustomBehavior::NONE);
30   ASSERT_EQ(1, iterator()->CountRuns());
31
32   int start, length;
33   EXPECT_EQ(UBIDI_LTR, iterator()->GetVisualRun(0, &start, &length));
34   EXPECT_EQ(0, start);
35   EXPECT_EQ(9, length);
36
37   int end;
38   UBiDiLevel level;
39   iterator()->GetLogicalRun(0, &end, &level);
40   EXPECT_EQ(9, end);
41   if (GetParam() == TextDirection::RIGHT_TO_LEFT)
42     EXPECT_EQ(2, level);
43   else
44     EXPECT_EQ(0, level);
45 }
46
47 TEST_P(BiDiLineIteratorTest, OnlyRTL) {
48   iterator()->Open(UTF8ToUTF16("诪讛 讛砖注讛"), GetParam(),
49                    BiDiLineIterator::CustomBehavior::NONE);
50   ASSERT_EQ(1, iterator()->CountRuns());
51
52   int start, length;
53   EXPECT_EQ(UBIDI_RTL, iterator()->GetVisualRun(0, &start, &length));
54   EXPECT_EQ(0, start);
55   EXPECT_EQ(7, length);
56
57   int end;
58   UBiDiLevel level;
59   iterator()->GetLogicalRun(0, &end, &level);
60   EXPECT_EQ(7, end);
61   EXPECT_EQ(1, level);
62 }
63
64 TEST_P(BiDiLineIteratorTest, Mixed) {
65   iterator()->Open(UTF8ToUTF16("讗谞讬 诪砖转诪砖 讘- Chrome 讻讚驻讚驻谉 讛讗讬谞讟专谞讟 砖诇讬"),
66                    GetParam(), BiDiLineIterator::CustomBehavior::NONE);
67   ASSERT_EQ(3, iterator()->CountRuns());
68
69   // We'll get completely different results depending on the top-level paragraph
70   // direction.
71   if (GetParam() == TextDirection::RIGHT_TO_LEFT) {
72     // If para direction is RTL, expect the LTR substring "Chrome" to be nested
73     // within the surrounding RTL text.
74     int start, length;
75     EXPECT_EQ(UBIDI_RTL, iterator()->GetVisualRun(0, &start, &length));
76     EXPECT_EQ(19, start);
77     EXPECT_EQ(20, length);
78     EXPECT_EQ(UBIDI_LTR, iterator()->GetVisualRun(1, &start, &length));
79     EXPECT_EQ(13, start);
80     EXPECT_EQ(6, length);
81     EXPECT_EQ(UBIDI_RTL, iterator()->GetVisualRun(2, &start, &length));
82     EXPECT_EQ(0, start);
83     EXPECT_EQ(13, length);
84
85     int end;
86     UBiDiLevel level;
87     iterator()->GetLogicalRun(0, &end, &level);
88     EXPECT_EQ(13, end);
89     EXPECT_EQ(1, level);
90     iterator()->GetLogicalRun(13, &end, &level);
91     EXPECT_EQ(19, end);
92     EXPECT_EQ(2, level);
93     iterator()->GetLogicalRun(19, &end, &level);
94     EXPECT_EQ(39, end);
95     EXPECT_EQ(1, level);
96   } else {
97     // If the para direction is LTR, expect the LTR substring "- Chrome " to be
98     // at the top level, with two nested RTL runs on either side.
99     int start, length;
100     EXPECT_EQ(UBIDI_RTL, iterator()->GetVisualRun(0, &start, &length));
101     EXPECT_EQ(0, start);
102     EXPECT_EQ(11, length);
103     EXPECT_EQ(UBIDI_LTR, iterator()->GetVisualRun(1, &start, &length));
104     EXPECT_EQ(11, start);
105     EXPECT_EQ(9, length);
106     EXPECT_EQ(UBIDI_RTL, iterator()->GetVisualRun(2, &start, &length));
107     EXPECT_EQ(20, start);
108     EXPECT_EQ(19, length);
109
110     int end;
111     UBiDiLevel level;
112     iterator()->GetLogicalRun(0, &end, &level);
113     EXPECT_EQ(11, end);
114     EXPECT_EQ(1, level);
115     iterator()->GetLogicalRun(11, &end, &level);
116     EXPECT_EQ(20, end);
117     EXPECT_EQ(0, level);
118     iterator()->GetLogicalRun(20, &end, &level);
119     EXPECT_EQ(39, end);
120     EXPECT_EQ(1, level);
121   }
122 }
123
124 TEST_P(BiDiLineIteratorTest, RTLPunctuationNoCustomBehavior) {
125   // This string features Hebrew characters interleaved with ASCII punctuation.
126   iterator()->Open(UTF8ToUTF16("讗!讘\"讙#讚$讛%讜&讝'讞(讟)讬*讱+讻,诇-诐.诪/"
127                                "谉:谞;住<注=祝>驻?抓@爪[拽\\专]砖^转_讗`讘{讙|讚}讛~讜"),
128                    GetParam(), BiDiLineIterator::CustomBehavior::NONE);
129
130   // Expect a single RTL run.
131   ASSERT_EQ(1, iterator()->CountRuns());
132
133   int start, length;
134   EXPECT_EQ(UBIDI_RTL, iterator()->GetVisualRun(0, &start, &length));
135   EXPECT_EQ(0, start);
136   EXPECT_EQ(65, length);
137
138   int end;
139   UBiDiLevel level;
140   iterator()->GetLogicalRun(0, &end, &level);
141   EXPECT_EQ(65, end);
142   EXPECT_EQ(1, level);
143 }
144
145 TEST_P(BiDiLineIteratorTest, RTLPunctuationAsURL) {
146   // This string features Hebrew characters interleaved with ASCII punctuation.
147   iterator()->Open(UTF8ToUTF16("讗!讘\"讙#讚$讛%讜&讝'讞(讟)讬*讱+讻,诇-诐.诪/"
148                                "谉:谞;住<注=祝>驻?抓@爪[拽\\专]砖^转_讗`讘{讙|讚}讛~讜"),
149                    GetParam(), BiDiLineIterator::CustomBehavior::AS_URL);
150
151   const int kStringSize = 65;
152
153   // Expect a primary RTL run, broken up by each of the 8 punctuation marks that
154   // are considered strong LTR (17 runs total).
155   struct {
156     int start;
157     UBiDiDirection dir;
158   } expected_runs[] = {
159       {0, UBIDI_RTL},  {5, UBIDI_LTR},   // '#'
160       {6, UBIDI_RTL},  {11, UBIDI_LTR},  // '&'
161       {12, UBIDI_RTL}, {27, UBIDI_LTR},  // '.'
162       {28, UBIDI_RTL}, {29, UBIDI_LTR},  // '/'
163       {30, UBIDI_RTL}, {31, UBIDI_LTR},  // ':'
164       {32, UBIDI_RTL}, {37, UBIDI_LTR},  // '='
165       {38, UBIDI_RTL}, {41, UBIDI_LTR},  // '?'
166       {42, UBIDI_RTL}, {43, UBIDI_LTR},  // '@'
167       {44, UBIDI_RTL},
168   };
169
170   ASSERT_EQ(arraysize(expected_runs),
171             static_cast<size_t>(iterator()->CountRuns()));
172
173   for (size_t i = 0; i < arraysize(expected_runs); ++i) {
174     const auto& expected_run = expected_runs[i];
175     int expected_run_end = i >= arraysize(expected_runs) - 1
176                                ? kStringSize
177                                : expected_runs[i + 1].start;
178
179     size_t visual_index = GetParam() == TextDirection::RIGHT_TO_LEFT
180                               ? arraysize(expected_runs) - 1 - i
181                               : i;
182     int start, length;
183     EXPECT_EQ(expected_run.dir,
184               iterator()->GetVisualRun(visual_index, &start, &length))
185         << "(i = " << i << ")";
186     EXPECT_EQ(expected_run.start, start) << "(i = " << i << ")";
187     EXPECT_EQ(expected_run_end - expected_run.start, length)
188         << "(i = " << i << ")";
189
190     int expected_level =
191         expected_run.dir == UBIDI_RTL
192             ? 1
193             : (GetParam() == TextDirection::RIGHT_TO_LEFT ? 2 : 0);
194     int end;
195     UBiDiLevel level;
196     iterator()->GetLogicalRun(expected_run.start, &end, &level);
197     EXPECT_EQ(expected_run_end, end) << "(i = " << i << ")";
198     EXPECT_EQ(expected_level, level) << "(i = " << i << ")";
199   }
200 }
201
202 INSTANTIATE_TEST_CASE_P(,
203                         BiDiLineIteratorTest,
204                         ::testing::Values(TextDirection::LEFT_TO_RIGHT,
205                                           TextDirection::RIGHT_TO_LEFT));
206
207 }  // namespace
208 }  // namespace i18n
209 }  // namespace base