CharBuffer.java 4.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135
  1. // Copyright (c) 2001, 2003, 2005, 2007 Per M.A. Bothner and Brainfood Inc.
  2. // This is free software; for terms and warranty disclaimer see ./COPYING.
  3. package gnu.lists;
  4. import gnu.text.Char;
  5. /** Editable character sequence using a buffer-gap implementation and
  6. * self-adjusting position.
  7. * Can implement (the text part of) an Emacs buffer, or a
  8. * javax.swing.text.AbstractDocument.Content
  9. */
  10. public class CharBuffer extends FString
  11. {
  12. StableManager manager;
  13. public CharBuffer(FString str) {
  14. super((CharSequence) str);
  15. manager = new StableManager(this);
  16. }
  17. public CharBuffer(int initialSize) {
  18. super(initialSize);
  19. setGapBounds(0, initialSize);
  20. manager = new StableManager(this);
  21. }
  22. protected CharBuffer() {
  23. manager = new StableManager(this);
  24. }
  25. public char[] getArray() { return (char[]) getBuffer(); }
  26. @Override public int startPos() { return manager.startPos(); }
  27. @Override public int endPos() { return manager.endPos(); }
  28. @Override public boolean isAfterPos(int ipos) { return manager.isAfterPos(ipos); }
  29. @Override public boolean hasNext(int ipos) { return manager.hasNext(ipos); }
  30. @Override public int nextPos(int ipos) { return manager.nextPos(ipos); }
  31. @Override public int copyPos(int ipos) { return manager.copyPos(ipos); }
  32. @Override public int nextIndex(int ipos) {
  33. return manager.nextIndex(ipos);
  34. }
  35. @Override public void releasePos(int ipos) { manager.releasePos(ipos); }
  36. @Override public int createPos(int index, boolean isAfter) {
  37. return manager.createPos(index, isAfter);
  38. }
  39. @Override
  40. public void insert(int where, int ch, boolean beforeMarkers) {
  41. super.insert(where, ch, beforeMarkers);
  42. if (beforeMarkers) {
  43. // Adjust markers at insertion point to be after inserted next.
  44. int len = ch >= 0x10000 ? 2 : 1;
  45. int oldPos = (getGapStart()-len) << 1;
  46. manager.adjustPositions(oldPos, oldPos + 1, len << 1);
  47. }
  48. }
  49. @Override
  50. public void insert(int where, String str, boolean beforeMarkers) {
  51. super.insert(where, str, beforeMarkers);
  52. if (beforeMarkers) {
  53. // Adjust markers at insertion point to be after inserted next.
  54. int len = str.length();
  55. int oldPos = (getGapStart()-len) << 1;
  56. manager.adjustPositions(oldPos, oldPos + 1, len << 1);
  57. }
  58. }
  59. @Override
  60. protected void gapReserve(int where, int needed) {
  61. manager.gapReserve(this, where, needed);
  62. }
  63. public String toString()
  64. {
  65. int len = size();
  66. int start = getSegment(0, len);
  67. return new String(getArray(), start, len);
  68. }
  69. /* #ifdef JAVA5 */
  70. public void writeTo(int start, int count, Appendable dest)
  71. throws java.io.IOException
  72. {
  73. if (dest instanceof java.io.Writer)
  74. writeTo(start, count, (java.io.Writer) dest);
  75. else
  76. dest.append(this, start, start+count);
  77. }
  78. public void writeTo(Appendable dest)
  79. throws java.io.IOException
  80. {
  81. writeTo(0, size(), dest);
  82. }
  83. /* #endif */
  84. public void dump()
  85. {
  86. System.err.println("Buffer Content dump. size:"+size()+" buffer:"+getArray().length);
  87. int gapStart = getGapStart();
  88. int gapEnd = getGapEnd();
  89. int[] positions = manager.positions;
  90. int free = manager.free;
  91. System.err.print("before gap: \"");
  92. System.err.print(new String(getArray(), 0, gapStart));
  93. System.err.println("\" (gapStart:"+gapStart+" gapEnd:"+gapEnd+')');
  94. System.err.print("after gap: \"");
  95. System.err.print(new String(getArray(), gapEnd, getArray().length-gapEnd));
  96. System.err.println("\"");
  97. int poslen = positions == null ? 0 : positions.length;
  98. System.err.println("Positions (size: "+poslen+" free:"+free+"):");
  99. boolean[] isFree = null;
  100. if (free != -2)
  101. {
  102. isFree = new boolean[positions.length];
  103. for (int i = free; i >= 0; i = positions[i])
  104. isFree[i] = true;
  105. }
  106. for (int i = 0; i < poslen; i++)
  107. {
  108. int pos = positions[i];
  109. if (free == -2 ? pos != StableManager.FREE_POSITION : ! isFree[i]) {
  110. int p = pos>>1;
  111. if (p > gapStart)
  112. p -= gapEnd-gapStart;
  113. System.err.println("position#"+i+": [raw:"+pos+"]="+p+" isAfter:"+(pos&1));
  114. }
  115. }
  116. }
  117. }