diff options
Diffstat (limited to 'WebCore/editing/TextIterator.cpp')
-rw-r--r-- | WebCore/editing/TextIterator.cpp | 95 |
1 files changed, 86 insertions, 9 deletions
diff --git a/WebCore/editing/TextIterator.cpp b/WebCore/editing/TextIterator.cpp index f617889..2d7e641 100644 --- a/WebCore/editing/TextIterator.cpp +++ b/WebCore/editing/TextIterator.cpp @@ -224,7 +224,9 @@ void TextIterator::advance() if (!m_handledNode) { if (renderer->isText() && m_node->nodeType() == Node::TEXT_NODE) // FIXME: What about CDATA_SECTION_NODE? m_handledNode = handleTextNode(); - else if (renderer && (renderer->isImage() || renderer->isWidget() || (renderer->element() && renderer->element()->isControl()))) + else if (renderer && (renderer->isImage() || renderer->isWidget() || + (renderer->node() && renderer->node()->isElementNode() && + static_cast<Element*>(renderer->node())->isFormControlElement()))) m_handledNode = handleReplacedElement(); else m_handledNode = handleNonTextNode(); @@ -247,7 +249,7 @@ void TextIterator::advance() parentNode = m_node->shadowParentNode(); } while (!next && parentNode) { - if (pastEnd && parentNode == m_endContainer || m_endContainer->isDescendantOf(parentNode)) + if ((pastEnd && parentNode == m_endContainer) || m_endContainer->isDescendantOf(parentNode)) return; bool haveRenderer = m_node->renderer(); m_node = parentNode; @@ -414,8 +416,8 @@ bool TextIterator::handleReplacedElement() return false; } - if (m_enterTextControls && (renderer->isTextArea() || renderer->isTextField())) { - m_node = static_cast<RenderTextControl*>(renderer)->innerTextElement(); + if (m_enterTextControls && renderer->isTextControl()) { + m_node = toRenderTextControl(renderer)->innerTextElement(); m_offset = 0; m_inShadowContent = true; return false; @@ -858,7 +860,7 @@ void SimplifiedBackwardsTextIterator::advance() if (!m_handledNode && canHaveChildrenForEditing(m_node) && m_node->parentNode() && - (!m_node->lastChild() || m_node == m_endNode && m_endOffset == 0)) { + (!m_node->lastChild() || (m_node == m_endNode && m_endOffset == 0))) { exitNode(); if (m_positionNode) { m_handledNode = true; @@ -1057,7 +1059,7 @@ void CharacterIterator::advance(int count) String CharacterIterator::string(int numChars) { Vector<UChar> result; - result.reserveCapacity(numChars); + result.reserveInitialCapacity(numChars); while (numChars > 0 && !atEnd()) { int runSize = min(numChars, length()); result.append(characters(), runSize); @@ -1081,6 +1083,81 @@ static PassRefPtr<Range> characterSubrange(CharacterIterator& it, int offset, in end->endContainer(), end->endOffset()); } +BackwardsCharacterIterator::BackwardsCharacterIterator() + : m_offset(0) + , m_runOffset(0) + , m_atBreak(true) +{ +} + +BackwardsCharacterIterator::BackwardsCharacterIterator(const Range* range) + : m_offset(0) + , m_runOffset(0) + , m_atBreak(true) + , m_textIterator(range) +{ + while (!atEnd() && !m_textIterator.length()) + m_textIterator.advance(); +} + +PassRefPtr<Range> BackwardsCharacterIterator::range() const +{ + RefPtr<Range> r = m_textIterator.range(); + if (!m_textIterator.atEnd()) { + if (m_textIterator.length() <= 1) + ASSERT(m_runOffset == 0); + else { + Node* n = r->startContainer(); + ASSERT(n == r->endContainer()); + int offset = r->endOffset() - m_runOffset; + ExceptionCode ec = 0; + r->setStart(n, offset - 1, ec); + r->setEnd(n, offset, ec); + ASSERT(!ec); + } + } + return r.release(); +} + +void BackwardsCharacterIterator::advance(int count) +{ + if (count <= 0) { + ASSERT(!count); + return; + } + + m_atBreak = false; + + int remaining = m_textIterator.length() - m_runOffset; + if (count < remaining) { + m_runOffset += count; + m_offset += count; + return; + } + + count -= remaining; + m_offset += remaining; + + for (m_textIterator.advance(); !atEnd(); m_textIterator.advance()) { + int runLength = m_textIterator.length(); + if (runLength == 0) + m_atBreak = true; + else { + if (count < runLength) { + m_runOffset = count; + m_offset += count; + return; + } + + count -= runLength; + m_offset += runLength; + } + } + + m_atBreak = true; + m_runOffset = 0; +} + // -------- WordAwareIterator::WordAwareIterator() @@ -1225,7 +1302,7 @@ inline SearchBuffer::SearchBuffer(const String& target, bool isCaseSensitive) ASSERT(!m_target.isEmpty()); size_t targetLength = target.length(); - m_buffer.reserveCapacity(max(targetLength * 8, minimumSearchBufferSize)); + m_buffer.reserveInitialCapacity(max(targetLength * 8, minimumSearchBufferSize)); m_overlap = m_buffer.capacity() / 4; // Grab the single global searcher. @@ -1481,7 +1558,7 @@ PassRefPtr<Range> TextIterator::rangeFromLocationAndLength(Element *scope, int r Position runEnd = VisiblePosition(runStart).next().deepEquivalent(); if (runEnd.isNotNull()) { ExceptionCode ec = 0; - textRunRange->setEnd(runEnd.node(), runEnd.offset(), ec); + textRunRange->setEnd(runEnd.node(), runEnd.m_offset, ec); ASSERT(!ec); } } @@ -1542,7 +1619,7 @@ UChar* plainTextToMallocAllocatedBuffer(const Range* r, unsigned& bufferLength, typedef pair<UChar*, unsigned> TextSegment; Vector<TextSegment>* textSegments = 0; Vector<UChar> textBuffer; - textBuffer.reserveCapacity(cMaxSegmentSize); + textBuffer.reserveInitialCapacity(cMaxSegmentSize); for (TextIterator it(r); !it.atEnd(); it.advance()) { if (textBuffer.size() && textBuffer.size() + it.length() > cMaxSegmentSize) { UChar* newSegmentBuffer = static_cast<UChar*>(malloc(textBuffer.size() * sizeof(UChar))); |