Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 /* | 1 /* |
| 2 * Copyright (C) 2000 Lars Knoll (knoll@kde.org) | 2 * Copyright (C) 2000 Lars Knoll (knoll@kde.org) |
| 3 * Copyright (C) 2003, 2004, 2006, 2007, 2008, 2009, 2010 Apple Inc. All right r eserved. | 3 * Copyright (C) 2003, 2004, 2006, 2007, 2008, 2009, 2010 Apple Inc. All right r eserved. |
| 4 * Copyright (C) 2010 Google Inc. All rights reserved. | 4 * Copyright (C) 2010 Google Inc. All rights reserved. |
| 5 * | 5 * |
| 6 * This library is free software; you can redistribute it and/or | 6 * This library is free software; you can redistribute it and/or |
| 7 * modify it under the terms of the GNU Library General Public | 7 * modify it under the terms of the GNU Library General Public |
| 8 * License as published by the Free Software Foundation; either | 8 * License as published by the Free Software Foundation; either |
| 9 * version 2 of the License, or (at your option) any later version. | 9 * version 2 of the License, or (at your option) any later version. |
| 10 * | 10 * |
| (...skipping 56 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 67 { | 67 { |
| 68 m_obj = object; | 68 m_obj = object; |
| 69 m_pos = offset; | 69 m_pos = offset; |
| 70 m_nextBreakablePosition = nextBreak; | 70 m_nextBreakablePosition = nextBreak; |
| 71 } | 71 } |
| 72 | 72 |
| 73 RenderObject* object() const { return m_obj; } | 73 RenderObject* object() const { return m_obj; } |
| 74 void setObject(RenderObject* object) { m_obj = object; } | 74 void setObject(RenderObject* object) { m_obj = object; } |
| 75 | 75 |
| 76 unsigned offset() const { return m_pos; } | 76 unsigned offset() const { return m_pos; } |
| 77 void setOffset(unsigned position) { m_pos = position; } | |
| 77 RenderObject* root() const { return m_root; } | 78 RenderObject* root() const { return m_root; } |
| 78 | 79 |
| 79 void fastIncrementInTextNode(); | 80 void fastIncrementInTextNode(); |
| 80 void increment(InlineBidiResolver* = 0, IncrementRule = FastIncrementInTextN ode); | 81 void increment(InlineBidiResolver* = 0, IncrementRule = FastIncrementInTextN ode); |
| 81 bool atEnd() const; | 82 bool atEnd() const; |
| 82 | 83 |
| 83 inline bool atTextParagraphSeparator() const | 84 inline bool atTextParagraphSeparator() const |
| 84 { | 85 { |
| 85 return m_obj && m_obj->preservesNewline() && m_obj->isText() && toRender Text(m_obj)->textLength() | 86 return m_obj && m_obj->preservesNewline() && m_obj->isText() && toRender Text(m_obj)->textLength() |
| 86 && !toRenderText(m_obj)->isWordBreak() && toRenderText(m_obj)->chara cterAt(m_pos) == '\n'; | 87 && !toRenderText(m_obj)->isWordBreak() && toRenderText(m_obj)->chara cterAt(m_pos) == '\n'; |
| 87 } | 88 } |
| 88 | 89 |
| 89 inline bool atParagraphSeparator() const | 90 inline bool atParagraphSeparator() const |
| 90 { | 91 { |
| 91 return (m_obj && m_obj->isBR()) || atTextParagraphSeparator(); | 92 return (m_obj && m_obj->isBR()) || atTextParagraphSeparator(); |
| 92 } | 93 } |
| 93 | 94 |
| 94 UChar characterAt(unsigned) const; | 95 UChar characterAt(unsigned) const; |
| 95 UChar current() const; | 96 UChar current() const; |
| 96 UChar previousInSameNode() const; | 97 UChar previousInSameNode() const; |
| 97 ALWAYS_INLINE WTF::Unicode::Direction direction() const; | 98 ALWAYS_INLINE WTF::Unicode::Direction direction() const; |
| 98 | 99 |
| 99 private: | 100 private: |
| 100 RenderObject* m_root; | 101 RenderObject* m_root; |
| 101 RenderObject* m_obj; | 102 RenderObject* m_obj; |
| 102 | 103 |
| 104 unsigned m_pos; | |
| 105 | |
| 103 // FIXME: These should be private. | 106 // FIXME: These should be private. |
|
pdr.
2013/12/30 01:05:16
Please remove this FIXME and the public: line (aft
gyuyoung-inactive
2013/12/30 01:07:12
Sure, I will do it as well. :)
| |
| 104 public: | 107 public: |
| 105 unsigned m_pos; | |
| 106 int m_nextBreakablePosition; | 108 int m_nextBreakablePosition; |
| 107 }; | 109 }; |
| 108 | 110 |
| 109 inline bool operator==(const InlineIterator& it1, const InlineIterator& it2) | 111 inline bool operator==(const InlineIterator& it1, const InlineIterator& it2) |
| 110 { | 112 { |
| 111 return it1.m_pos == it2.m_pos && it1.object() == it2.object(); | 113 return it1.offset() == it2.offset() && it1.object() == it2.object(); |
| 112 } | 114 } |
| 113 | 115 |
| 114 inline bool operator!=(const InlineIterator& it1, const InlineIterator& it2) | 116 inline bool operator!=(const InlineIterator& it1, const InlineIterator& it2) |
| 115 { | 117 { |
| 116 return it1.m_pos != it2.m_pos || it1.object() != it2.object(); | 118 return it1.offset() != it2.offset() || it1.object() != it2.object(); |
| 117 } | 119 } |
| 118 | 120 |
| 119 static inline WTF::Unicode::Direction embedCharFromDirection(TextDirection dir, EUnicodeBidi unicodeBidi) | 121 static inline WTF::Unicode::Direction embedCharFromDirection(TextDirection dir, EUnicodeBidi unicodeBidi) |
| 120 { | 122 { |
| 121 using namespace WTF::Unicode; | 123 using namespace WTF::Unicode; |
| 122 if (unicodeBidi == Embed) | 124 if (unicodeBidi == Embed) |
| 123 return dir == RTL ? RightToLeftEmbedding : LeftToRightEmbedding; | 125 return dir == RTL ? RightToLeftEmbedding : LeftToRightEmbedding; |
| 124 return dir == RTL ? RightToLeftOverride : LeftToRightOverride; | 126 return dir == RTL ? RightToLeftOverride : LeftToRightOverride; |
| 125 } | 127 } |
| 126 | 128 |
| (...skipping 308 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 435 inline void InlineBidiResolver::increment() | 437 inline void InlineBidiResolver::increment() |
| 436 { | 438 { |
| 437 m_current.increment(this, InlineIterator::FastIncrementInIsolatedRenderer); | 439 m_current.increment(this, InlineIterator::FastIncrementInIsolatedRenderer); |
| 438 } | 440 } |
| 439 | 441 |
| 440 template <> | 442 template <> |
| 441 inline bool InlineBidiResolver::isEndOfLine(const InlineIterator& end) | 443 inline bool InlineBidiResolver::isEndOfLine(const InlineIterator& end) |
| 442 { | 444 { |
| 443 bool inEndOfLine = m_current == end || m_current.atEnd() || (inIsolate() && m_current.object() == end.object()); | 445 bool inEndOfLine = m_current == end || m_current.atEnd() || (inIsolate() && m_current.object() == end.object()); |
| 444 if (inIsolate() && inEndOfLine) { | 446 if (inIsolate() && inEndOfLine) { |
| 445 m_current.moveTo(m_current.object(), end.m_pos, m_current.m_nextBreakabl ePosition); | 447 m_current.moveTo(m_current.object(), end.offset(), m_current.m_nextBreak ablePosition); |
| 446 m_last = m_current; | 448 m_last = m_current; |
| 447 updateStatusLastFromCurrentDirection(WTF::Unicode::OtherNeutral); | 449 updateStatusLastFromCurrentDirection(WTF::Unicode::OtherNeutral); |
| 448 } | 450 } |
| 449 return inEndOfLine; | 451 return inEndOfLine; |
| 450 } | 452 } |
| 451 | 453 |
| 452 static inline bool isIsolatedInline(RenderObject* object) | 454 static inline bool isIsolatedInline(RenderObject* object) |
| 453 { | 455 { |
| 454 ASSERT(object); | 456 ASSERT(object); |
| 455 return object->isRenderInline() && isIsolated(object->style()->unicodeBidi() ); | 457 return object->isRenderInline() && isIsolated(object->style()->unicodeBidi() ); |
| (...skipping 116 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 572 bool haveNextMidpoint = (lineMidpointState.currentMidpoint < lineMidpointSta te.numMidpoints); | 574 bool haveNextMidpoint = (lineMidpointState.currentMidpoint < lineMidpointSta te.numMidpoints); |
| 573 InlineIterator nextMidpoint; | 575 InlineIterator nextMidpoint; |
| 574 if (haveNextMidpoint) | 576 if (haveNextMidpoint) |
| 575 nextMidpoint = lineMidpointState.midpoints[lineMidpointState.currentMidp oint]; | 577 nextMidpoint = lineMidpointState.midpoints[lineMidpointState.currentMidp oint]; |
| 576 if (lineMidpointState.betweenMidpoints) { | 578 if (lineMidpointState.betweenMidpoints) { |
| 577 if (!(haveNextMidpoint && nextMidpoint.object() == obj)) | 579 if (!(haveNextMidpoint && nextMidpoint.object() == obj)) |
| 578 return; | 580 return; |
| 579 // This is a new start point. Stop ignoring objects and | 581 // This is a new start point. Stop ignoring objects and |
| 580 // adjust our start. | 582 // adjust our start. |
| 581 lineMidpointState.betweenMidpoints = false; | 583 lineMidpointState.betweenMidpoints = false; |
| 582 start = nextMidpoint.m_pos; | 584 start = nextMidpoint.offset(); |
| 583 lineMidpointState.currentMidpoint++; | 585 lineMidpointState.currentMidpoint++; |
| 584 if (start < end) | 586 if (start < end) |
| 585 return adjustMidpointsAndAppendRunsForObjectIfNeeded(obj, start, end , resolver, behavior, tracker); | 587 return adjustMidpointsAndAppendRunsForObjectIfNeeded(obj, start, end , resolver, behavior, tracker); |
| 586 } else { | 588 } else { |
| 587 if (!haveNextMidpoint || (obj != nextMidpoint.object())) { | 589 if (!haveNextMidpoint || (obj != nextMidpoint.object())) { |
| 588 appendRunObjectIfNecessary(obj, start, end, resolver, behavior, trac ker); | 590 appendRunObjectIfNecessary(obj, start, end, resolver, behavior, trac ker); |
| 589 return; | 591 return; |
| 590 } | 592 } |
| 591 | 593 |
| 592 // An end midpoint has been encountered within our object. We | 594 // An end midpoint has been encountered within our object. We |
| 593 // need to go ahead and append a run with our endpoint. | 595 // need to go ahead and append a run with our endpoint. |
| 594 if (nextMidpoint.m_pos + 1 <= end) { | 596 if (nextMidpoint.offset() + 1 <= end) { |
| 595 lineMidpointState.betweenMidpoints = true; | 597 lineMidpointState.betweenMidpoints = true; |
| 596 lineMidpointState.currentMidpoint++; | 598 lineMidpointState.currentMidpoint++; |
| 597 if (nextMidpoint.m_pos != UINT_MAX) { // UINT_MAX means stop at the object and don't nclude any of it. | 599 if (nextMidpoint.offset() != UINT_MAX) { // UINT_MAX means stop at t he object and don't nclude any of it. |
| 598 if (nextMidpoint.m_pos + 1 > start) | 600 if (nextMidpoint.offset() + 1 > start) |
| 599 appendRunObjectIfNecessary(obj, start, nextMidpoint.m_pos + 1, resolver, behavior, tracker); | 601 appendRunObjectIfNecessary(obj, start, nextMidpoint.offset() + 1, resolver, behavior, tracker); |
| 600 return adjustMidpointsAndAppendRunsForObjectIfNeeded(obj, nextMi dpoint.m_pos + 1, end, resolver, behavior, tracker); | 602 return adjustMidpointsAndAppendRunsForObjectIfNeeded(obj, nextMi dpoint.offset() + 1, end, resolver, behavior, tracker); |
| 601 } | 603 } |
| 602 } else { | 604 } else { |
| 603 appendRunObjectIfNecessary(obj, start, end, resolver, behavior, trac ker); | 605 appendRunObjectIfNecessary(obj, start, end, resolver, behavior, trac ker); |
| 604 } | 606 } |
| 605 } | 607 } |
| 606 } | 608 } |
| 607 | 609 |
| 608 static inline void addFakeRunIfNecessary(RenderObject* obj, unsigned start, unsi gned end, InlineBidiResolver& resolver, IsolateTracker& tracker) | 610 static inline void addFakeRunIfNecessary(RenderObject* obj, unsigned start, unsi gned end, InlineBidiResolver& resolver, IsolateTracker& tracker) |
| 609 { | 611 { |
| 610 tracker.setMidpointStateForRootIsolate(resolver.midpointState()); | 612 tracker.setMidpointStateForRootIsolate(resolver.midpointState()); |
| 611 adjustMidpointsAndAppendRunsForObjectIfNeeded(obj, start, obj->length(), res olver, AppendingFakeRun, tracker); | 613 adjustMidpointsAndAppendRunsForObjectIfNeeded(obj, start, obj->length(), res olver, AppendingFakeRun, tracker); |
| 612 } | 614 } |
| 613 | 615 |
| 614 template <> | 616 template <> |
| 615 inline void InlineBidiResolver::appendRun() | 617 inline void InlineBidiResolver::appendRun() |
| 616 { | 618 { |
| 617 if (!m_emptyRun && !m_eor.atEnd() && !m_reachedEndOfLine) { | 619 if (!m_emptyRun && !m_eor.atEnd() && !m_reachedEndOfLine) { |
| 618 // Keep track of when we enter/leave "unicode-bidi: isolate" inlines. | 620 // Keep track of when we enter/leave "unicode-bidi: isolate" inlines. |
| 619 // Initialize our state depending on if we're starting in the middle of such an inline. | 621 // Initialize our state depending on if we're starting in the middle of such an inline. |
| 620 // FIXME: Could this initialize from this->inIsolate() instead of walkin g up the render tree? | 622 // FIXME: Could this initialize from this->inIsolate() instead of walkin g up the render tree? |
| 621 IsolateTracker isolateTracker(numberOfIsolateAncestors(m_sor)); | 623 IsolateTracker isolateTracker(numberOfIsolateAncestors(m_sor)); |
| 622 int start = m_sor.m_pos; | 624 int start = m_sor.offset(); |
| 623 RenderObject* obj = m_sor.object(); | 625 RenderObject* obj = m_sor.object(); |
| 624 while (obj && obj != m_eor.object() && obj != m_endOfRunAtEndOfLine.obje ct()) { | 626 while (obj && obj != m_eor.object() && obj != m_endOfRunAtEndOfLine.obje ct()) { |
| 625 if (isolateTracker.inIsolate()) | 627 if (isolateTracker.inIsolate()) |
| 626 addFakeRunIfNecessary(obj, start, obj->length(), *this, isolateT racker); | 628 addFakeRunIfNecessary(obj, start, obj->length(), *this, isolateT racker); |
| 627 else | 629 else |
| 628 adjustMidpointsAndAppendRunsForObjectIfNeeded(obj, start, obj->l ength(), *this, AppendingRunsForObject, isolateTracker); | 630 adjustMidpointsAndAppendRunsForObjectIfNeeded(obj, start, obj->l ength(), *this, AppendingRunsForObject, isolateTracker); |
| 629 // FIXME: start/obj should be an InlineIterator instead of two separ ate variables. | 631 // FIXME: start/obj should be an InlineIterator instead of two separ ate variables. |
| 630 start = 0; | 632 start = 0; |
| 631 obj = bidiNextSkippingEmptyInlines(m_sor.root(), obj, &isolateTracke r); | 633 obj = bidiNextSkippingEmptyInlines(m_sor.root(), obj, &isolateTracke r); |
| 632 } | 634 } |
| 633 bool isEndOfLine = obj == m_endOfLine.object() && !m_endOfLine.m_pos; | 635 bool isEndOfLine = obj == m_endOfLine.object() && !m_endOfLine.offset(); |
| 634 if (obj && !isEndOfLine) { | 636 if (obj && !isEndOfLine) { |
| 635 unsigned pos = obj == m_eor.object() ? m_eor.m_pos : INT_MAX; | 637 unsigned pos = obj == m_eor.object() ? m_eor.offset() : INT_MAX; |
| 636 if (obj == m_endOfRunAtEndOfLine.object() && m_endOfRunAtEndOfLine.m _pos <= pos) { | 638 if (obj == m_endOfRunAtEndOfLine.object() && m_endOfRunAtEndOfLine.o ffset() <= pos) { |
| 637 m_reachedEndOfLine = true; | 639 m_reachedEndOfLine = true; |
| 638 pos = m_endOfRunAtEndOfLine.m_pos; | 640 pos = m_endOfRunAtEndOfLine.offset(); |
| 639 } | 641 } |
| 640 // It's OK to add runs for zero-length RenderObjects, just don't mak e the run larger than it should be | 642 // It's OK to add runs for zero-length RenderObjects, just don't mak e the run larger than it should be |
| 641 int end = obj->length() ? pos + 1 : 0; | 643 int end = obj->length() ? pos + 1 : 0; |
| 642 if (isolateTracker.inIsolate()) | 644 if (isolateTracker.inIsolate()) |
| 643 addFakeRunIfNecessary(obj, start, end, *this, isolateTracker); | 645 addFakeRunIfNecessary(obj, start, end, *this, isolateTracker); |
| 644 else | 646 else |
| 645 adjustMidpointsAndAppendRunsForObjectIfNeeded(obj, start, end, * this, AppendingRunsForObject, isolateTracker); | 647 adjustMidpointsAndAppendRunsForObjectIfNeeded(obj, start, end, * this, AppendingRunsForObject, isolateTracker); |
| 646 } | 648 } |
| 647 | 649 |
| 648 if (isEndOfLine) | 650 if (isEndOfLine) |
| 649 m_reachedEndOfLine = true; | 651 m_reachedEndOfLine = true; |
| 650 m_eor.increment(); | 652 m_eor.increment(); |
| 651 m_sor = m_eor; | 653 m_sor = m_eor; |
| 652 } | 654 } |
| 653 | 655 |
| 654 m_direction = WTF::Unicode::OtherNeutral; | 656 m_direction = WTF::Unicode::OtherNeutral; |
| 655 m_status.eor = WTF::Unicode::OtherNeutral; | 657 m_status.eor = WTF::Unicode::OtherNeutral; |
| 656 } | 658 } |
| 657 | 659 |
| 658 } | 660 } |
| 659 | 661 |
| 660 #endif // InlineIterator_h | 662 #endif // InlineIterator_h |
| OLD | NEW |