You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

LineBreakStatus.java 6.3KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160
  1. /*
  2. * Licensed to the Apache Software Foundation (ASF) under one or more
  3. * contributor license agreements. See the NOTICE file distributed with
  4. * this work for additional information regarding copyright ownership.
  5. * The ASF licenses this file to You under the Apache License, Version 2.0
  6. * (the "License"); you may not use this file except in compliance with
  7. * the License. You may obtain a copy of the License at
  8. *
  9. * http://www.apache.org/licenses/LICENSE-2.0
  10. *
  11. * Unless required by applicable law or agreed to in writing, software
  12. * distributed under the License is distributed on an "AS IS" BASIS,
  13. * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  14. * See the License for the specific language governing permissions and
  15. * limitations under the License.
  16. */
  17. /* $Id$ */
  18. package org.apache.fop.text.linebreak;
  19. /**
  20. * This class is meant for supporting the Unicode line breaking algorithm.
  21. * See <a href="http://unicode.org/reports/tr14/">UTR 14</a>.
  22. *
  23. */
  24. public class LineBreakStatus {
  25. /** Constant indicating a Direct Break */
  26. public static final byte DIRECT_BREAK = LineBreakUtils.DIRECT_BREAK;
  27. /** Constant indicating an Indirect Break */
  28. public static final byte INDIRECT_BREAK = LineBreakUtils.INDIRECT_BREAK;
  29. /** Constant indicating a Combining Indirect Break */
  30. public static final byte COMBINING_INDIRECT_BREAK = LineBreakUtils.COMBINING_INDIRECT_BREAK;
  31. /** Constant indicating a Combining Prohibited Break */
  32. public static final byte COMBINING_PROHIBITED_BREAK = LineBreakUtils.COMBINING_PROHIBITED_BREAK;
  33. /** Constant indicating a Prohibited Break */
  34. public static final byte PROHIBITED_BREAK = LineBreakUtils.PROHIBITED_BREAK;
  35. /** Constant indicating a Explicit Break */
  36. public static final byte EXPLICIT_BREAK = LineBreakUtils.EXPLICIT_BREAK;
  37. private byte leftClass;
  38. private boolean hadSpace;
  39. /**
  40. * Resets the class to the same state as if new LineBreakStatus() had just been called.
  41. */
  42. public LineBreakStatus() {
  43. reset();
  44. }
  45. /**
  46. * Reset the status.
  47. * This method will reset the status to the initial state. It is meant
  48. * for recycling objects.
  49. */
  50. public void reset() {
  51. leftClass = -1;
  52. hadSpace = false;
  53. }
  54. /**
  55. * Check whether a line break may happen.
  56. * The function returns the line breaking status of the point before the given character.
  57. * The algorithm is the table driven algorithm described in the Unicode
  58. * <a href="http://unicode.org/reports/tr14/#PairBasedImplementation">technical report #14</a>.
  59. * The pair table is taken from @see LineBreakUtils
  60. *
  61. * TODO: Better handling for AI, SA, CB and other line break classes.
  62. *
  63. * @param c The character.
  64. * @return the break action to be taken
  65. */
  66. public byte nextChar(char c) {
  67. byte currentClass = LineBreakUtils.getLineBreakProperty(c);
  68. if (currentClass == LineBreakUtils.LINE_BREAK_PROPERTY_AI
  69. || leftClass == LineBreakUtils.LINE_BREAK_PROPERTY_XX) {
  70. currentClass = LineBreakUtils.LINE_BREAK_PROPERTY_AL;
  71. } else if (currentClass == LineBreakUtils.LINE_BREAK_PROPERTY_NL) {
  72. currentClass = LineBreakUtils.LINE_BREAK_PROPERTY_BK;
  73. }
  74. if (leftClass == -1) {
  75. if (currentClass == LineBreakUtils.LINE_BREAK_PROPERTY_LF) {
  76. leftClass = LineBreakUtils.LINE_BREAK_PROPERTY_BK;
  77. } else {
  78. leftClass = currentClass;
  79. if (leftClass == LineBreakUtils.LINE_BREAK_PROPERTY_CM) {
  80. leftClass = LineBreakUtils.LINE_BREAK_PROPERTY_ID;
  81. }
  82. }
  83. // LB 2a
  84. return PROHIBITED_BREAK;
  85. } else if (!(leftClass != LineBreakUtils.LINE_BREAK_PROPERTY_BK
  86. && (leftClass != LineBreakUtils.LINE_BREAK_PROPERTY_CR
  87. || currentClass == LineBreakUtils.LINE_BREAK_PROPERTY_LF)
  88. )) {
  89. reset();
  90. if (currentClass == LineBreakUtils.LINE_BREAK_PROPERTY_LF) {
  91. leftClass = LineBreakUtils.LINE_BREAK_PROPERTY_BK;
  92. }
  93. return EXPLICIT_BREAK;
  94. } else if (currentClass == LineBreakUtils.LINE_BREAK_PROPERTY_BK
  95. || currentClass == LineBreakUtils.LINE_BREAK_PROPERTY_LF) {
  96. leftClass = LineBreakUtils.LINE_BREAK_PROPERTY_BK;
  97. return PROHIBITED_BREAK;
  98. } else if (currentClass == LineBreakUtils.LINE_BREAK_PROPERTY_CR) {
  99. leftClass = LineBreakUtils.LINE_BREAK_PROPERTY_CR;
  100. return PROHIBITED_BREAK;
  101. } else if (currentClass == LineBreakUtils.LINE_BREAK_PROPERTY_SP) {
  102. hadSpace = true;
  103. return PROHIBITED_BREAK;
  104. } else {
  105. boolean savedHadSpace = hadSpace;
  106. hadSpace = false;
  107. switch (LineBreakUtils.getLineBreakPairProperty(leftClass, currentClass)) {
  108. case LineBreakUtils.PROHIBITED_BREAK :
  109. leftClass = currentClass;
  110. return PROHIBITED_BREAK;
  111. case LineBreakUtils.DIRECT_BREAK :
  112. leftClass = currentClass;
  113. return DIRECT_BREAK;
  114. case LineBreakUtils.INDIRECT_BREAK :
  115. leftClass = currentClass;
  116. if (savedHadSpace) {
  117. return INDIRECT_BREAK;
  118. } else {
  119. return PROHIBITED_BREAK;
  120. }
  121. case LineBreakUtils.COMBINING_INDIRECT_BREAK :
  122. if (savedHadSpace) {
  123. leftClass = currentClass;
  124. return COMBINING_INDIRECT_BREAK;
  125. } else {
  126. return PROHIBITED_BREAK;
  127. }
  128. case LineBreakUtils.COMBINING_PROHIBITED_BREAK :
  129. if (savedHadSpace) {
  130. leftClass = currentClass;
  131. }
  132. return COMBINING_PROHIBITED_BREAK;
  133. default :
  134. throw new RuntimeException("duh");
  135. }
  136. }
  137. }
  138. /**
  139. * for debugging only
  140. */
  141. /*
  142. public static void main(String args[]) {
  143. LineBreakStatus lbs = new LineBreakStatus();
  144. lbs.nextChar('\n');
  145. lbs.nextChar('\n');
  146. lbs.nextChar('x');
  147. }
  148. */
  149. }