1 /* GENERATED SOURCE. DO NOT MODIFY. */ 2 // 2016 and later: Unicode, Inc. and others. 3 // License & terms of use: http://www.unicode.org/copyright.html#License 4 /* 5 ******************************************************************************* 6 * Copyright (C) 2007-2013, International Business Machines 7 * Corporation and others. All Rights Reserved. 8 ******************************************************************************* 9 */ 10 11 package android.icu.dev.test.bidi; 12 13 import java.util.Arrays; 14 15 import org.junit.Test; 16 17 import android.icu.text.Bidi; 18 import android.icu.text.BidiRun; 19 import android.icu.testsharding.MainTestShard; 20 21 /** 22 * Regression test for Bidi class override. 23 * 24 * @author Lina Kemmel, Matitiahu Allouche 25 */ 26 27 @MainTestShard 28 public class TestBidi extends BidiFmwk { 29 30 private static final int MAXLEN = 256; 31 private static final String levelString = "............................"; 32 33 @Test 34 public void testBidi() { 35 Bidi bidi; 36 Bidi bidiLine; 37 38 logln("\nEntering TestBidi"); 39 bidi = new Bidi(MAXLEN, 0); 40 bidiLine = new Bidi(); 41 42 doTests(bidi, bidiLine, false); 43 doTests(bidi, bidiLine, true); 44 doMisc(); 45 logln("\nExiting TestBidi"); 46 } 47 48 private void doTests(Bidi bidi, Bidi bidiLine, boolean countRunsFirst) { 49 int testNumber; 50 String string; 51 int lineStart; 52 byte paraLevel; 53 int bidiTestCount = TestData.testCount(); 54 55 for (testNumber = 0; testNumber < bidiTestCount; ++testNumber) { 56 TestData test = TestData.getTestData(testNumber); 57 string = getStringFromDirProps(test.dirProps); 58 paraLevel = test.paraLevel; 59 try { 60 bidi.setPara(string, paraLevel, null); 61 logln("Bidi.setPara(tests[" + testNumber + "] OK, direction " 62 + bidi.getDirection() + " paraLevel " 63 + paraLevel); 64 } catch (Exception e) { 65 errln("Bidi.setPara(tests[" + testNumber + "] failed, direction " 66 + bidi.getDirection() + " paraLevel " 67 + paraLevel); 68 } 69 lineStart = test.lineStart; 70 if (lineStart == -1) { 71 doTest(bidi, testNumber, test, 0, countRunsFirst); 72 } else { 73 try { 74 bidiLine = bidi.setLine(lineStart, test.lineLimit); 75 logln("Bidi.setLine(" + lineStart + ", " + test.lineLimit 76 + "), in tests[" + testNumber + "] OK, direction " 77 + bidiLine.getDirection() + " paraLevel " 78 + bidiLine.getBaseLevel()); 79 doTest(bidiLine, testNumber, test, lineStart, countRunsFirst); 80 } catch (Exception e) { 81 errln("Bidi.setLine(" + lineStart + ", " + test.lineLimit 82 + "), in runAll test[" + testNumber + "] failed"); 83 } 84 /* do it again using createLineBidi instead of setLine */ 85 try { 86 bidiLine = bidi.createLineBidi(lineStart, test.lineLimit); 87 logln("Bidi.createLineBidi(" + lineStart + ", " + test.lineLimit 88 + "), in tests[" + testNumber + "] OK, direction " 89 + bidiLine.getDirection() + " paraLevel " 90 + bidiLine.getBaseLevel()); 91 doTest(bidiLine, testNumber, test, lineStart, countRunsFirst); 92 } catch (Exception e) { 93 errln("Bidi.createLineBidi(" + lineStart + ", " + test.lineLimit 94 + "), in runAll test[" + testNumber + "] failed"); 95 } 96 } 97 } 98 } 99 100 private void doTest(Bidi bidi, int testNumber, TestData test, 101 int lineStart, boolean countRunsFirst) { 102 short[] dirProps = test.dirProps; 103 byte[] levels = test.levels; 104 int[] visualMap = test.visualMap; 105 int i, len = bidi.getLength(), logicalIndex = -1, runCount = 0; 106 byte level, level2; 107 108 if (countRunsFirst) { 109 logln("Calling Bidi.countRuns() first."); 110 try { 111 runCount = bidi.countRuns(); 112 } catch (IllegalStateException e) { 113 errln("Bidi.countRuns(test[" + testNumber + "]) failed"); 114 } 115 } else { 116 logln("Calling Bidi.getLogicalMap() first."); 117 } 118 119 _testReordering(bidi, testNumber); 120 121 for (i = 0; i < len; ++i) { 122 logln(i + " " + bidi.getLevelAt(i) + " " + levelString 123 + TestData.dirPropNames[dirProps[lineStart + i]] + " " 124 + bidi.getVisualIndex(i)); 125 } 126 127 log("\n-----levels:"); 128 for (i = 0; i < len; ++i) { 129 if (i > 0) { 130 log(","); 131 } 132 log(" " + bidi.getLevelAt(i)); 133 } 134 135 log("\n--reordered:"); 136 for (i = 0; i < len; ++i) { 137 if (i > 0) { 138 log(","); 139 } 140 log(" " + bidi.getVisualIndex(i)); 141 } 142 log("\n"); 143 144 assertEquals("\nFailure in Bidi.getDirection(test[" + testNumber + "])", 145 test.direction, bidi.getDirection()); 146 assertEquals("\nFailure in Bidi.getParaLevel(test[" + testNumber + "])", 147 test.resultLevel, bidi.getParaLevel()); 148 149 for (i = 0; i < len; ++i) { 150 assertEquals("\nFailure in Bidi.getLevelAt(" + i + 151 ") in test[" + testNumber + "]", 152 levels[i], bidi.getLevelAt(i)); 153 } 154 155 for (i = 0; i < len; ++i) { 156 try { 157 logicalIndex = bidi.getVisualIndex(i); 158 } catch (Throwable th) { 159 errln("Bidi.getVisualIndex(" + i + ") in test[" + testNumber 160 + "] failed"); 161 } 162 if(visualMap[i] != logicalIndex) { 163 assertEquals("\nFailure in Bidi.getVisualIndex(" + i + 164 ") in test[" + testNumber + "])", 165 visualMap[i], logicalIndex); 166 } 167 } 168 169 if (!countRunsFirst) { 170 try { 171 runCount = bidi.countRuns(); 172 } catch (IllegalStateException e) { 173 errln("Bidi.countRuns(test[" + testNumber + "]) failed"); 174 } 175 } 176 177 BidiRun run; 178 179 for (logicalIndex = 0; logicalIndex < len; ) { 180 level = bidi.getLevelAt(logicalIndex); 181 run = bidi.getLogicalRun(logicalIndex); 182 logicalIndex = run.getLimit(); 183 level2 = run.getEmbeddingLevel(); 184 assertEquals("Logical " + run.toString() + 185 " in test[" + testNumber + "]: wrong level", 186 level, level2); 187 if (--runCount < 0) { 188 errln("Bidi.getLogicalRun(test[" + testNumber 189 + "]): wrong number of runs compared to Bidi.countRuns() = " 190 + bidi.countRuns()); 191 } 192 } 193 if (runCount != 0) { 194 errln("Bidi.getLogicalRun(test[" + testNumber 195 + "]): wrong number of runs compared to Bidi.countRuns() = " 196 + bidi.countRuns()); 197 } 198 199 log("\n\n"); 200 } 201 202 private void _testReordering(Bidi bidi, int testNumber) { 203 int[] logicalMap1; 204 int[] logicalMap2; 205 int[] logicalMap3; 206 int[] visualMap1; 207 int[] visualMap2; 208 int[] visualMap3; 209 int[] visualMap4 = new int[MAXLEN]; 210 byte[] levels; 211 int i, length = bidi.getLength(), 212 destLength = bidi.getResultLength(); 213 int runCount, visualIndex, logicalIndex = -1, logicalStart, runLength; 214 boolean odd; 215 216 if(length <= 0) { 217 return; 218 } 219 /* get the logical and visual maps from the object */ 220 logicalMap1 = bidi.getLogicalMap(); 221 if (logicalMap1 == null) { 222 errln("getLogicalMap in test " + testNumber + " is null"); 223 logicalMap1 = new int[0]; 224 } 225 226 visualMap1 = bidi.getVisualMap(); 227 228 if (visualMap1 == null) { 229 errln("getVisualMap() in test " + testNumber + " is null"); 230 visualMap1 = new int[0]; 231 } 232 233 /* invert them both */ 234 visualMap2 = Bidi.invertMap(logicalMap1); 235 logicalMap2 = Bidi.invertMap(visualMap1); 236 237 /* get them from the levels array, too */ 238 levels = bidi.getLevels(); 239 240 if (levels == null || levels.length != length) { 241 errln("getLevels() in test " + testNumber + " failed"); 242 } 243 244 logicalMap3 = Bidi.reorderLogical(levels); 245 visualMap3 = Bidi.reorderVisual(levels); 246 247 /* get the visual map from the runs, too */ 248 try { 249 runCount = bidi.countRuns(); 250 } catch (IllegalStateException e) { 251 errln("countRuns() in test " + testNumber + " failed"); 252 runCount = 0; 253 } 254 255 logln("\n---- " + runCount + " runs"); 256 visualIndex = 0; 257 BidiRun run; 258 for (i = 0; i < runCount; ++i) { 259 run = bidi.getVisualRun(i); 260 if (run == null) { 261 errln("null visual run encountered at index " + i + 262 ", in test " + testNumber); 263 continue; 264 } 265 odd = run.isOddRun(); 266 logicalStart = run.getStart(); 267 runLength = run.getLength(); 268 log("(" + (run.isOddRun() ? "R" : "L")); 269 log(" @" + run.getStart() + '[' + run.getLength() + "])\n"); 270 if (!odd) { 271 do { /* LTR */ 272 visualMap4[visualIndex++] = logicalStart++; 273 } while (--runLength > 0); 274 } else { 275 logicalStart += runLength; /* logicalLimit */ 276 do { /* RTL */ 277 visualMap4[visualIndex++] = --logicalStart; 278 } while (--runLength > 0); 279 } 280 } 281 log("\n"); 282 283 /* print all the maps */ 284 logln("logical maps:"); 285 for (i = 0; i < length; ++i) { 286 log(logicalMap1[i] + " "); 287 } 288 log("\n"); 289 for (i = 0; i < length; ++i) { 290 log(logicalMap2[i] + " "); 291 } 292 log("\n"); 293 for (i = 0; i < length; ++i) { 294 log(logicalMap3[i] + " "); 295 } 296 297 log("\nvisual maps:\n"); 298 for (i = 0; i < destLength; ++i) { 299 log(visualMap1[i] + " "); 300 } 301 log("\n"); 302 for (i = 0; i < destLength; ++i) { 303 log(visualMap2[i] + " "); 304 } 305 log("\n"); 306 for (i = 0; i < length; ++i) { 307 log(visualMap3[i] + " "); 308 } 309 log("\n"); 310 for (i = 0; i < length; ++i) { 311 log(visualMap4[i] + " "); 312 } 313 log("\n"); 314 315 /* check that the indexes are the same between these and Bidi.getLogical/VisualIndex() */ 316 for (i = 0; i < length; ++i) { 317 if (logicalMap1[i] != logicalMap2[i]) { 318 errln("Error in tests[" + testNumber + "]: (logicalMap1[" + i + 319 "] == " + logicalMap1[i] + ") != (logicalMap2[" + i + 320 "] == " + logicalMap2[i] + ")"); 321 } 322 if (logicalMap1[i] != logicalMap3[i]) { 323 errln("Error in tests[" + testNumber + "]: (logicalMap1[" + i + 324 "] == " + logicalMap1[i] + ") != (logicalMap3[" + i + 325 "] == " + logicalMap3[i] + ")"); 326 } 327 if (visualMap1[i] != visualMap2[i]) { 328 errln("Error in tests[" + testNumber + "]: (visualMap1[" + i + 329 "] == " + visualMap1[i] + ") != (visualMap2[" + i + 330 "] == " + visualMap2[i] + ")"); 331 } 332 if (visualMap1[i] != visualMap3[i]) { 333 errln("Error in tests[" + testNumber + "]: (visualMap1[" + i + 334 "] == " + visualMap1[i] + ") != (visualMap3[" + i + 335 "] == " + visualMap3[i] + ")"); 336 } 337 if (visualMap1[i] != visualMap4[i]) { 338 errln("Error in tests[" + testNumber + "]: (visualMap1[" + i + 339 "] == " + visualMap1[i] + ") != (visualMap4[" + i + 340 "] == " + visualMap4[i] + ")"); 341 } 342 try { 343 visualIndex = bidi.getVisualIndex(i); 344 } catch (Exception e) { 345 errln("Bidi.getVisualIndex(" + i + ") failed in tests[" + 346 testNumber + "]"); 347 } 348 if (logicalMap1[i] != visualIndex) { 349 errln("Error in tests[" + testNumber + "]: (logicalMap1[" + i + 350 "] == " + logicalMap1[i] + ") != (Bidi.getVisualIndex(" + i + 351 ") == " + visualIndex + ")"); 352 } 353 try { 354 logicalIndex = bidi.getLogicalIndex(i); 355 } catch (Exception e) { 356 errln("Bidi.getLogicalIndex(" + i + ") failed in tests[" + 357 testNumber + "]"); 358 } 359 if (visualMap1[i] != logicalIndex) { 360 errln("Error in tests[" + testNumber + "]: (visualMap1[" + i + 361 "] == " + visualMap1[i] + ") != (Bidi.getLogicalIndex(" + i + 362 ") == " + logicalIndex + ")"); 363 } 364 } 365 } 366 367 private String getStringFromDirProps(short[] dirProps) { 368 int i; 369 370 if (dirProps == null) { 371 return null; 372 } 373 int length = dirProps.length; 374 char[] buffer = new char[length]; 375 376 /* this part would have to be modified for UTF-x */ 377 for (i = 0; i < length; ++i) { 378 buffer[i] = charFromDirProp[dirProps[i]]; 379 } 380 return new String(buffer); 381 } 382 383 private void doMisc() { 384 /* Miscellaneous tests to exercize less popular code paths */ 385 Bidi bidi = new Bidi(120, 66), bidiLine; 386 387 assertEquals("\nwriteReverse should return an empty string", 388 "", Bidi.writeReverse("", 0)); 389 390 bidi.setPara("", Bidi.LTR, null); 391 assertEquals("\nwriteReordered should return an empty string", 392 "", bidi.writeReordered(0)); 393 394 bidi.setPara("abc", Bidi.LTR, null); 395 assertEquals("\ngetRunStart should return 0", 396 0, bidi.getRunStart(0)); 397 assertEquals("\ngetRunLimit should return 3", 398 3, bidi.getRunLimit(0)); 399 400 bidi.setPara("abc ", Bidi.RTL, null); 401 bidiLine = bidi.setLine(0, 6); 402 for (int i = 3; i < 6; i++) { 403 assertEquals("\nTrailing space at " + i + " should get paragraph level", 404 Bidi.RTL, bidiLine.getLevelAt(i)); 405 } 406 407 bidi.setPara("abc def", Bidi.RTL, null); 408 bidiLine = bidi.setLine(0, 6); 409 for (int i = 3; i < 6; i++) { 410 assertEquals("\nTrailing space at " + i + " should get paragraph level", 411 Bidi.RTL, bidiLine.getLevelAt(i)); 412 } 413 414 bidi.setPara("abcdefghi ", Bidi.RTL, null); 415 bidiLine = bidi.setLine(0, 6); 416 for (int i = 3; i < 6; i++) { 417 assertEquals("\nTrailing char at " + i + " should get level 2", 418 2, bidiLine.getLevelAt(i)); 419 } 420 421 bidi.setReorderingOptions(Bidi.OPTION_REMOVE_CONTROLS); 422 bidi.setPara("\u200eabc def", Bidi.RTL, null); 423 bidiLine = bidi.setLine(0, 6); 424 assertEquals("\nWrong result length", 5, bidiLine.getResultLength()); 425 426 bidi.setPara("abcdefghi", Bidi.LTR, null); 427 bidiLine = bidi.setLine(0, 6); 428 assertEquals("\nWrong direction #1", Bidi.LTR, bidiLine.getDirection()); 429 430 bidi.setPara("", Bidi.LTR, null); 431 byte[] levels = bidi.getLevels(); 432 assertEquals("\nWrong number of level elements", 0, levels.length); 433 assertEquals("\nWrong number of runs #1", 0, bidi.countRuns()); 434 435 bidi.setPara(" ", Bidi.RTL, null); 436 bidiLine = bidi.setLine(0, 6); 437 assertEquals("\nWrong number of runs #2", 1, bidiLine.countRuns()); 438 439 bidi.setPara("a\u05d0 bc", Bidi.RTL, null); 440 bidiLine = bidi.setLine(0, 6); 441 assertEquals("\nWrong direction #2", Bidi.MIXED, bidi.getDirection()); 442 assertEquals("\nWrong direction #3", Bidi.MIXED, bidiLine.getDirection()); 443 assertEquals("\nWrong number of runs #3", 2, bidiLine.countRuns()); 444 445 int[] map = Bidi.reorderLogical(null); 446 assertTrue("\nWe should have got a null map #1", map == null); 447 map = Bidi.reorderLogical(new byte[] {0,126, 127}); 448 assertTrue("\nWe should have got a null map #2", map == null); 449 map = Bidi.reorderVisual(null); 450 assertTrue("\nWe should have got a null map #3", map == null); 451 map = Bidi.reorderVisual(new byte[] {0, -1, 4}); 452 assertTrue("\nWe should have got a null map #4", map == null); 453 454 map = Bidi.invertMap(null); 455 assertTrue("\nWe should have got a null map #5", map == null); 456 map = Bidi.invertMap(new int[] {0,1,-1,5,4}); 457 assertTrue("\nUnexpected inverted Map", 458 Arrays.equals(map, new int[] {0,1,-1,-1,4,3})); 459 460 bidi.setPara("", Bidi.LTR, null); 461 map = bidi.getLogicalMap(); 462 assertTrue("\nMap should have length==0 #1", map.length == 0); 463 map = bidi.getVisualMap(); 464 assertTrue("\nMap should have length==0 #2", map.length == 0); 465 466 /* test BidiRun.toString and allocation of run memory > 1 */ 467 bidi.setPara("abc", Bidi.LTR, null); 468 assertEquals("\nWrong run display", "BidiRun 0 - 3 @ 0", 469 bidi.getLogicalRun(0).toString()); 470 471 /* test REMOVE_BIDI_CONTROLS together with DO_MIRRORING */ 472 bidi.setPara("abc\u200e", Bidi.LTR, null); 473 String out = bidi.writeReordered(Bidi.REMOVE_BIDI_CONTROLS | Bidi.DO_MIRRORING); 474 assertEquals("\nWrong result #1", "abc", out); 475 476 /* test inverse Bidi with marks and contextual orientation */ 477 bidi.setReorderingMode(Bidi.REORDER_INVERSE_LIKE_DIRECT); 478 bidi.setReorderingOptions(Bidi.OPTION_INSERT_MARKS); 479 bidi.setPara("", Bidi.LEVEL_DEFAULT_RTL, null); 480 out = bidi.writeReordered(0); 481 assertEquals("\nWrong result #2", "", out); 482 bidi.setPara(" ", Bidi.LEVEL_DEFAULT_RTL, null); 483 out = bidi.writeReordered(0); 484 assertEquals("\nWrong result #3", " ", out); 485 bidi.setPara("abc", Bidi.LEVEL_DEFAULT_RTL, null); 486 out = bidi.writeReordered(0); 487 assertEquals("\nWrong result #4", "abc", out); 488 bidi.setPara("\u05d0\u05d1", Bidi.LEVEL_DEFAULT_RTL, null); 489 out = bidi.writeReordered(0); 490 assertEquals("\nWrong result #5", "\u05d1\u05d0", out); 491 bidi.setPara("abc \u05d0\u05d1", Bidi.LEVEL_DEFAULT_RTL, null); 492 out = bidi.writeReordered(0); 493 assertEquals("\nWrong result #6", "\u05d1\u05d0 abc", out); 494 bidi.setPara("\u05d0\u05d1 abc", Bidi.LEVEL_DEFAULT_RTL, null); 495 out = bidi.writeReordered(0); 496 assertEquals("\nWrong result #7", "\u200fabc \u05d1\u05d0", out); 497 bidi.setPara("\u05d0\u05d1 abc .-=", Bidi.LEVEL_DEFAULT_RTL, null); 498 out = bidi.writeReordered(0); 499 assertEquals("\nWrong result #8", "\u200f=-. abc \u05d1\u05d0", out); 500 bidi.orderParagraphsLTR(true); 501 bidi.setPara("\n\r \n\rabc\n\u05d0\u05d1\rabc \u05d2\u05d3\n\r" + 502 "\u05d4\u05d5 abc\n\u05d6\u05d7 abc .-=\r\n" + 503 "-* \u05d8\u05d9 abc .-=", Bidi.LEVEL_DEFAULT_RTL, null); 504 out = bidi.writeReordered(0); 505 assertEquals("\nWrong result #9", 506 "\n\r \n\rabc\n\u05d1\u05d0\r\u05d3\u05d2 abc\n\r" + 507 "\u200fabc \u05d5\u05d4\n\u200f=-. abc \u05d7\u05d6\r\n" + 508 "\u200f=-. abc \u05d9\u05d8 *-", out); 509 510 bidi.setPara("\u05d0 \t", Bidi.LTR, null); 511 out = bidi.writeReordered(0); 512 assertEquals("\nWrong result #10", "\u05D0\u200e \t", out); 513 bidi.setPara("\u05d0 123 \t\u05d1 123 \u05d2", Bidi.LTR, null); 514 out = bidi.writeReordered(0); 515 assertEquals("\nWrong result #11", "\u05d0 \u200e123\u200e \t\u05d2 123 \u05d1", out); 516 bidi.setPara("\u05d0 123 \u0660\u0661 ab", Bidi.LTR, null); 517 out = bidi.writeReordered(0); 518 assertEquals("\nWrong result #12", "\u05d0 \u200e123 \u200e\u0660\u0661 ab", out); 519 bidi.setPara("ab \t", Bidi.RTL, null); 520 out = bidi.writeReordered(0); 521 assertEquals("\nWrong result #13", "\u200f\t ab", out); 522 523 /* check exceeding para level */ 524 bidi = new Bidi(); 525 bidi.setPara("A\u202a\u05d0\u202aC\u202c\u05d1\u202cE", (byte)(Bidi.MAX_EXPLICIT_LEVEL - 1), null); 526 assertEquals("\nWrong level at index 2", Bidi.MAX_EXPLICIT_LEVEL, bidi.getLevelAt(2)); 527 528 /* check 1-char runs with RUNS_ONLY */ 529 bidi.setReorderingMode(Bidi.REORDER_RUNS_ONLY); 530 bidi.setPara("a \u05d0 b \u05d1 c \u05d2 d ", Bidi.LTR, null); 531 assertEquals("\nWrong number of runs #4", 14, bidi.countRuns()); 532 533 /* test testGetBaseDirection to verify fast string direction detection function */ 534 /* mixed start with L */ 535 String mixedEnglishFirst = "\u0061\u0627\u0032\u06f3\u0061\u0034"; 536 assertEquals("\nWrong direction through fast detection #1", Bidi.LTR, Bidi.getBaseDirection(mixedEnglishFirst)); 537 /* mixed start with AL */ 538 String mixedArabicFirst = "\u0661\u0627\u0662\u06f3\u0061\u0664"; 539 assertEquals("\nWrong direction through fast detection #2", Bidi.RTL, Bidi.getBaseDirection(mixedArabicFirst)); 540 /* mixed Start with R */ 541 String mixedHebrewFirst = "\u05EA\u0627\u0662\u06f3\u0061\u0664"; 542 assertEquals("\nWrong direction through fast detection #3", Bidi.RTL, Bidi.getBaseDirection(mixedHebrewFirst)); 543 /* all AL (Arabic. Persian) */ 544 String persian = "\u0698\u067E\u0686\u06AF"; 545 assertEquals("\nWrong direction through fast detection #4", Bidi.RTL, Bidi.getBaseDirection(persian)); 546 /* all R (Hebrew etc.) */ 547 String hebrew = "\u0590\u05D5\u05EA\u05F1"; 548 assertEquals("\nWrong direction through fast detection #5", Bidi.RTL, Bidi.getBaseDirection(hebrew)); 549 /* all L (English) */ 550 String english = "\u0071\u0061\u0066"; 551 assertEquals("\nWrong direction through fast detection #6", Bidi.LTR, Bidi.getBaseDirection(english)); 552 /* mixed start with weak AL an then L */ 553 String startWeakAL = "\u0663\u0071\u0061\u0066"; 554 assertEquals("\nWrong direction through fast detection #7", Bidi.LTR, Bidi.getBaseDirection(startWeakAL)); 555 /* mixed start with weak L and then AL */ 556 String startWeakL = "\u0031\u0698\u067E\u0686\u06AF"; 557 assertEquals("\nWrong direction through fast detection #8", Bidi.RTL, Bidi.getBaseDirection(startWeakL)); 558 /* empty */ 559 String empty = ""; 560 assertEquals("\nWrong direction through fast detection #9", Bidi.NEUTRAL, Bidi.getBaseDirection(empty)); 561 /* surrogate character */ 562 String surrogateChar = "\uD800\uDC00"; 563 assertEquals("\nWrong direction through fast detection #10", Bidi.LTR, Bidi.getBaseDirection(surrogateChar)); 564 /* all weak L (English digits) */ 565 String allEnglishDigits = "\u0031\u0032\u0033"; 566 assertEquals("\nWrong direction through fast detection #11", Bidi.NEUTRAL, Bidi.getBaseDirection(allEnglishDigits)); 567 /* all weak AL (Arabic digits) */ 568 String allArabicDigits = "\u0663\u0664\u0665"; 569 assertEquals("\nWrong direction through fast detection #12", Bidi.NEUTRAL, Bidi.getBaseDirection(allArabicDigits)); 570 /* null string */ 571 String nullString = null; 572 assertEquals("\nWrong direction through fast detection #13", Bidi.NEUTRAL, Bidi.getBaseDirection(nullString)); 573 /* first L (English) others are R (Hebrew etc.) */ 574 String startEnglishOthersHebrew = "\u0071\u0590\u05D5\u05EA\u05F1"; 575 assertEquals("\nWrong direction through fast detection #14", Bidi.LTR, Bidi.getBaseDirection(startEnglishOthersHebrew)); 576 /* last R (Hebrew etc.) others are weak L (English Digits) */ 577 String lastHebrewOthersEnglishDigit = "\u0031\u0032\u0033\u05F1"; 578 assertEquals("\nWrong direction through fast detection #15", Bidi.RTL, Bidi.getBaseDirection(lastHebrewOthersEnglishDigit)); 579 } 580 581 @Test 582 public void testExplicitLevel0() { 583 // The following used to fail with an error, see ICU ticket #12922. 584 String text = "\u202d\u05d0"; 585 byte[] embeddings = new byte[2]; // all 0 586 int flags = Bidi.DIRECTION_DEFAULT_LEFT_TO_RIGHT; // 0x7e 587 Bidi bidi = new Bidi(text.toCharArray(), 0, embeddings, 0, text.length(), flags); 588 assertEquals("resolved level at 0", 1, bidi.getLevelAt(0)); 589 assertEquals("resolved level at 1", 1, bidi.getLevelAt(1)); 590 591 flags = java.text.Bidi.DIRECTION_DEFAULT_LEFT_TO_RIGHT; // -2 592 java.text.Bidi jb = new java.text.Bidi(text.toCharArray(), 0, embeddings, 0, text.length(), flags); 593 assertEquals("java.text resolved level at 0", 1, jb.getLevelAt(0)); 594 assertEquals("java.text resolved level at 1", 1, jb.getLevelAt(1)); 595 } 596 } 597