18e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project/** 28e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * Copyright (C) 2006, 2007 Apple Inc. All rights reserved. 3635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project * (C) 2008 Torch Mobile Inc. All rights reserved. (http://www.torchmobile.com/) 48e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * 58e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * This library is free software; you can redistribute it and/or 68e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * modify it under the terms of the GNU Library General Public 78e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * License as published by the Free Software Foundation; either 88e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * version 2 of the License, or (at your option) any later version. 98e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * 108e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * This library is distributed in the hope that it will be useful, 118e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * but WITHOUT ANY WARRANTY; without even the implied warranty of 128e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 138e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * Library General Public License for more details. 148e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * 158e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * You should have received a copy of the GNU Library General Public License 168e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * along with this library; see the file COPYING.LIB. If not, write to 178e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, 188e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * Boston, MA 02110-1301, USA. 198e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project * 208e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project */ 218e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 228e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "config.h" 238e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "RenderTextControl.h" 248e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 255f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian#include "AXObjectCache.h" 268e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "Editor.h" 278e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "Event.h" 288e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "EventNames.h" 298e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "Frame.h" 308e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "HTMLBRElement.h" 31f486d19d62f1bc33246748b14b14a9dfa617b57fIain Merrick#include "HTMLFormControlElement.h" 326b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner#include "HTMLInputElement.h" 338e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "HTMLNames.h" 348e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "HitTestResult.h" 3565f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch#include "Position.h" 368f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian#include "RenderLayer.h" 37635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project#include "RenderText.h" 388e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "ScrollbarTheme.h" 398e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "SelectionController.h" 40635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project#include "Text.h" 418f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian#include "TextControlInnerElements.h" 428e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project#include "TextIterator.h" 43ab9e7a118cf1ea2e3a93dce683b2ded3e7291ddbBen Murdoch#include "TextRun.h" 442fc2651226baac27029e38c9d6ef883fa32084dbSteve Block#include <wtf/unicode/CharacterNames.h> 458e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 468e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectusing namespace std; 478e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 488e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectnamespace WebCore { 498e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 508e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectusing namespace HTMLNames; 518e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 528e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project// Value chosen by observation. This can be tweaked. 538e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectstatic const int minColorContrastValue = 1300; 548e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 558e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectstatic Color disabledTextColor(const Color& textColor, const Color& backgroundColor) 568e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 578e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // The explicit check for black is an optimization for the 99% case (black on white). 588e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // This also means that black on black will turn into grey on black when disabled. 598e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project Color disabledColor; 608e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (textColor.rgb() == Color::black || differenceSquared(textColor, Color::white) > differenceSquared(backgroundColor, Color::white)) 618e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project disabledColor = textColor.light(); 628e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project else 638e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project disabledColor = textColor.dark(); 648e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 658e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // If there's not very much contrast between the disabled color and the background color, 668e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // just leave the text color alone. We don't want to change a good contrast color scheme so that it has really bad contrast. 678e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // If the the contrast was already poor, then it doesn't do any good to change it to a different poor contrast color scheme. 688e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (differenceSquared(disabledColor, backgroundColor) < minColorContrastValue) 698e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return textColor; 708e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 718e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return disabledColor; 728e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 738e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 74231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve BlockRenderTextControl::RenderTextControl(Node* node, bool placeholderVisible) 758e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project : RenderBlock(node) 76231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block , m_placeholderVisible(placeholderVisible) 77643ca7872b450ea4efacab6188849e5aac2ba161Steve Block , m_lastChangeWasUserEdit(false) 788e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 798e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 808e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 818e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source ProjectRenderTextControl::~RenderTextControl() 828e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 838e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // The children renderers have already been destroyed by destroyLeftoverChildren 84635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (m_innerText) 858e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project m_innerText->detach(); 868e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 878e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 888f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qianvoid RenderTextControl::styleDidChange(StyleDifference diff, const RenderStyle* oldStyle) 898e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 908e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project RenderBlock::styleDidChange(diff, oldStyle); 918e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 928e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (m_innerText) { 938f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian RenderBlock* textBlockRenderer = toRenderBlock(m_innerText->renderer()); 948e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project RefPtr<RenderStyle> textBlockStyle = createInnerTextStyle(style()); 95635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // We may have set the width and the height in the old style in layout(). 96635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // Reset them now to avoid getting a spurious layout hint. 978e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project textBlockRenderer->style()->setHeight(Length()); 988e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project textBlockRenderer->style()->setWidth(Length()); 99231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block setInnerTextStyle(textBlockStyle); 100231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block } 101231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block} 102231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 103231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Blockvoid RenderTextControl::setInnerTextStyle(PassRefPtr<RenderStyle> style) 104231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block{ 105231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block if (m_innerText) { 106231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block RefPtr<RenderStyle> textStyle = style; 107231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block m_innerText->renderer()->setStyle(textStyle); 1088e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project for (Node* n = m_innerText->firstChild(); n; n = n->traverseNextNode(m_innerText.get())) { 1098e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (n->renderer()) 110231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block n->renderer()->setStyle(textStyle); 1118e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 1128e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 1138e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 1148e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1158f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qianstatic inline bool updateUserModifyProperty(Node* node, RenderStyle* style) 1168f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian{ 1178f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian bool isEnabled = true; 1188f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian bool isReadOnlyControl = false; 1198f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian 1208f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian if (node->isElementNode()) { 1215f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian Element* element = static_cast<Element*>(node); 1225f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian isEnabled = element->isEnabledFormControl(); 1235f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian isReadOnlyControl = element->isReadOnlyFormControl(); 1248f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian } 1258f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian 1268f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian style->setUserModify((isReadOnlyControl || !isEnabled) ? READ_ONLY : READ_WRITE_PLAINTEXT_ONLY); 1278f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian return !isEnabled; 1288f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian} 1298f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian 130635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Projectvoid RenderTextControl::adjustInnerTextStyle(const RenderStyle* startStyle, RenderStyle* textBlockStyle) const 1318e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 1328e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // The inner block, if present, always has its direction set to LTR, 1338e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // so we need to inherit the direction from the element. 1348e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project textBlockStyle->setDirection(style()->direction()); 1358e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1368f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian bool disabled = updateUserModifyProperty(node(), textBlockStyle); 1378f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian if (disabled) 138e78cbe89e6f337f2f1fe40315be88f742b547151Steve Block textBlockStyle->setColor(disabledTextColor(textBlockStyle->visitedDependentColor(CSSPropertyColor), startStyle->visitedDependentColor(CSSPropertyBackgroundColor))); 1398e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 1408e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 141635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Projectvoid RenderTextControl::createSubtreeIfNeeded(TextControlInnerElement* innerBlock) 1428e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 143635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (!m_innerText) { 144635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // Create the text block element 145635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // For non-search fields, there is no intermediate innerBlock as the shadow node. 146635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // m_innerText will be the shadow node in that case. 147635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project RenderStyle* parentStyle = innerBlock ? innerBlock->renderer()->style() : style(); 1482fc2651226baac27029e38c9d6ef883fa32084dbSteve Block m_innerText = TextControlInnerTextElement::create(document(), innerBlock ? 0 : toHTMLElement(node())); 149635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project m_innerText->attachInnerElement(innerBlock ? innerBlock : node(), createInnerTextStyle(parentStyle), renderArena()); 150635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project } 1518e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 1528e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 153635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Projectint RenderTextControl::textBlockHeight() const 1548e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 15521939df44de1705786c545cd1bf519d47250322dBen Murdoch return height() - borderAndPaddingHeight(); 1568e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 1578e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 158635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Projectint RenderTextControl::textBlockWidth() const 1598e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 16021939df44de1705786c545cd1bf519d47250322dBen Murdoch return width() - borderAndPaddingWidth() - m_innerText->renderBox()->paddingLeft() - m_innerText->renderBox()->paddingRight(); 1618e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 1628e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1638e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid RenderTextControl::updateFromElement() 1648e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 1658f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian updateUserModifyProperty(node(), m_innerText->renderer()->style()); 166635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project} 1678e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 168635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Projectvoid RenderTextControl::setInnerTextValue(const String& innerTextValue) 169635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project{ 170dcc8cf2e65d1aa555cce12431a16547e66b469eeSteve Block String value = innerTextValue; 171635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (value != text() || !m_innerText->hasChildNodes()) { 172635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (value != text()) { 173545e470e52f0ac6a3a072bf559c796b42c6066b6Ben Murdoch if (Frame* frame = this->frame()) { 174635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project frame->editor()->clearUndoRedoOperations(); 1755f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian 1765f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian if (AXObjectCache::accessibilityEnabled()) 177231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block document()->axObjectCache()->postNotification(this, AXObjectCache::AXValueChanged, false); 1785f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian } 179635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project } 1808e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 181635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project ExceptionCode ec = 0; 182635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project m_innerText->setInnerText(value, ec); 183635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project ASSERT(!ec); 184635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 185635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (value.endsWith("\n") || value.endsWith("\r")) { 1865af96e2c7b73ebc627c6894727826a7576d31758Leon Clarke m_innerText->appendChild(HTMLBRElement::create(document()), ec); 187635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project ASSERT(!ec); 1888e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 189635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 190d0825bca7fe65beaee391d30da42e937db621564Steve Block // We set m_lastChangeWasUserEdit to false since this change was not explicitly made by the user (say, via typing on the keyboard), see <rdar://problem/5359921>. 191643ca7872b450ea4efacab6188849e5aac2ba161Steve Block m_lastChangeWasUserEdit = false; 1928e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 1938e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 1945f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian static_cast<Element*>(node())->setFormControlValueMatchesRenderer(true); 1958e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 1968e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 197643ca7872b450ea4efacab6188849e5aac2ba161Steve Blockvoid RenderTextControl::setLastChangeWasUserEdit(bool lastChangeWasUserEdit) 1988e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 199643ca7872b450ea4efacab6188849e5aac2ba161Steve Block m_lastChangeWasUserEdit = lastChangeWasUserEdit; 200643ca7872b450ea4efacab6188849e5aac2ba161Steve Block document()->setIgnoreAutofocus(lastChangeWasUserEdit); 2018e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 2028e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 20328040489d744e0c5d475a88663056c9040ed5320Teng-Hui Zhuint RenderTextControl::selectionStart() const 2048e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 205545e470e52f0ac6a3a072bf559c796b42c6066b6Ben Murdoch Frame* frame = this->frame(); 2068e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (!frame) 2078e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return 0; 208d0147a863b872ecaa451ab0dce2a348760e99e2cBen Murdoch 209d0147a863b872ecaa451ab0dce2a348760e99e2cBen Murdoch HTMLElement* innerText = innerTextElement(); 210d0147a863b872ecaa451ab0dce2a348760e99e2cBen Murdoch // Do not call innerTextElement() in the function arguments as creating a VisiblePosition 211d0147a863b872ecaa451ab0dce2a348760e99e2cBen Murdoch // from frame->selection->start() can blow us from underneath. Also, function ordering is 212d0147a863b872ecaa451ab0dce2a348760e99e2cBen Murdoch // usually dependent on the compiler. 213d0147a863b872ecaa451ab0dce2a348760e99e2cBen Murdoch return RenderTextControl::indexForVisiblePosition(innerText, frame->selection()->start()); 2148e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 2158e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 21628040489d744e0c5d475a88663056c9040ed5320Teng-Hui Zhuint RenderTextControl::selectionEnd() const 2178e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 218545e470e52f0ac6a3a072bf559c796b42c6066b6Ben Murdoch Frame* frame = this->frame(); 2198e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (!frame) 2208e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return 0; 221d0147a863b872ecaa451ab0dce2a348760e99e2cBen Murdoch 222d0147a863b872ecaa451ab0dce2a348760e99e2cBen Murdoch HTMLElement* innerText = innerTextElement(); 223d0147a863b872ecaa451ab0dce2a348760e99e2cBen Murdoch // Do not call innerTextElement() in the function arguments as creating a VisiblePosition 224d0147a863b872ecaa451ab0dce2a348760e99e2cBen Murdoch // from frame->selection->end() can blow us from underneath. Also, function ordering is 225d0147a863b872ecaa451ab0dce2a348760e99e2cBen Murdoch // usually dependent on the compiler. 226d0147a863b872ecaa451ab0dce2a348760e99e2cBen Murdoch return RenderTextControl::indexForVisiblePosition(innerText, frame->selection()->end()); 2278e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 2288e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 229e14391e94c850b8bd03680c23b38978db68687a8John Reckbool RenderTextControl::hasVisibleTextArea() const 2308e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 231e14391e94c850b8bd03680c23b38978db68687a8John Reck return style()->visibility() == HIDDEN || !m_innerText || !m_innerText->renderer() || !m_innerText->renderBox()->height(); 2328e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 2338e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 234e14391e94c850b8bd03680c23b38978db68687a8John Reckvoid setSelectionRange(Node* node, int start, int end) 2358e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 236e14391e94c850b8bd03680c23b38978db68687a8John Reck ASSERT(node); 237e14391e94c850b8bd03680c23b38978db68687a8John Reck node->document()->updateLayoutIgnorePendingStylesheets(); 2388e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 239e14391e94c850b8bd03680c23b38978db68687a8John Reck if (!node->renderer() || !node->renderer()->isTextControl()) 240e14391e94c850b8bd03680c23b38978db68687a8John Reck return; 2418e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 2428e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project end = max(end, 0); 2438e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project start = min(max(start, 0), end); 2448e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 245e14391e94c850b8bd03680c23b38978db68687a8John Reck RenderTextControl* control = toRenderTextControl(node->renderer()); 2468e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 247e14391e94c850b8bd03680c23b38978db68687a8John Reck if (control->hasVisibleTextArea()) { 248e14391e94c850b8bd03680c23b38978db68687a8John Reck control->cacheSelection(start, end); 2498e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 2508e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 251e14391e94c850b8bd03680c23b38978db68687a8John Reck VisiblePosition startPosition = control->visiblePositionForIndex(start); 2528e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project VisiblePosition endPosition; 2538e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (start == end) 2548e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project endPosition = startPosition; 2558e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project else 256e14391e94c850b8bd03680c23b38978db68687a8John Reck endPosition = control->visiblePositionForIndex(end); 2578e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 2580bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch // startPosition and endPosition can be null position for example when 2590bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch // "-webkit-user-select: none" style attribute is specified. 2600bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch if (startPosition.isNotNull() && endPosition.isNotNull()) { 26181bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch ASSERT(startPosition.deepEquivalent().deprecatedNode()->shadowAncestorNode() == node && endPosition.deepEquivalent().deprecatedNode()->shadowAncestorNode() == node); 2620bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch } 2638f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian VisibleSelection newSelection = VisibleSelection(startPosition, endPosition); 2648e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 265e14391e94c850b8bd03680c23b38978db68687a8John Reck if (Frame* frame = node->document()->frame()) 2668e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project frame->selection()->setSelection(newSelection); 2678e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 2688e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 269d0147a863b872ecaa451ab0dce2a348760e99e2cBen Murdochbool RenderTextControl::isSelectableElement(HTMLElement* innerText, Node* node) 2706b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner{ 271d0147a863b872ecaa451ab0dce2a348760e99e2cBen Murdoch if (!node || !innerText) 2726b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner return false; 273d0147a863b872ecaa451ab0dce2a348760e99e2cBen Murdoch 274d0147a863b872ecaa451ab0dce2a348760e99e2cBen Murdoch if (node->rootEditableElement() == innerText) 2756b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner return true; 2766b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner 277d0147a863b872ecaa451ab0dce2a348760e99e2cBen Murdoch if (!innerText->contains(node)) 2786b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner return false; 2796b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner 2806b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner Node* shadowAncestor = node->shadowAncestorNode(); 2816b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner return shadowAncestor && (shadowAncestor->hasTagName(textareaTag) 2826b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner || (shadowAncestor->hasTagName(inputTag) && static_cast<HTMLInputElement*>(shadowAncestor)->isTextField())); 2836b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner} 2846b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner 28565f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdochstatic inline void setContainerAndOffsetForRange(Node* node, int offset, Node*& containerNode, int& offsetInContainer) 28665f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch{ 28765f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch if (node->isTextNode()) { 28865f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch containerNode = node; 28965f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch offsetInContainer = offset; 29065f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch } else { 29165f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch containerNode = node->parentNode(); 29265f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch offsetInContainer = node->nodeIndex() + offset; 29365f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch } 29465f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch} 29565f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch 296a94275402997c11dd2e778633dacf4b7e630a35dBen MurdochPassRefPtr<Range> RenderTextControl::selection(int start, int end) const 2978e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 29865f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch ASSERT(start <= end); 299a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch if (!m_innerText) 300a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch return 0; 301a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch 30265f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch if (!m_innerText->firstChild()) 30365f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch return Range::create(document(), m_innerText, 0, m_innerText, 0); 30465f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch 30565f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch int offset = 0; 30665f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch Node* startNode = 0; 30765f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch Node* endNode = 0; 30865f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch for (Node* node = m_innerText->firstChild(); node; node = node->traverseNextNode(m_innerText.get())) { 30965f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch ASSERT(!node->firstChild()); 31065f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch ASSERT(node->isTextNode() || node->hasTagName(brTag)); 31165f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch int length = node->isTextNode() ? lastOffsetInNode(node) : 1; 31265f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch 31365f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch if (offset <= start && start <= offset + length) 31465f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch setContainerAndOffsetForRange(node, start - offset, startNode, start); 31565f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch 31665f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch if (offset <= end && end <= offset + length) { 31765f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch setContainerAndOffsetForRange(node, end - offset, endNode, end); 31865f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch break; 31965f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch } 32065f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch 32165f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch offset += length; 32265f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch } 32365f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch 32465f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch if (!startNode || !endNode) 32565f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch return 0; 32665f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch 32765f03d4f644ce73618e5f4f50dd694b26f55ae12Ben Murdoch return Range::create(document(), startNode, start, endNode, end); 3288e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 3298e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 33028040489d744e0c5d475a88663056c9040ed5320Teng-Hui ZhuVisiblePosition RenderTextControl::visiblePositionForIndex(int index) const 3318e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 3328e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (index <= 0) 33381bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch return VisiblePosition(Position(m_innerText.get(), 0, Position::PositionIsOffsetInAnchor), DOWNSTREAM); 3348e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ExceptionCode ec = 0; 3358e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project RefPtr<Range> range = Range::create(document()); 3368e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project range->selectNodeContents(m_innerText.get(), ec); 337635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project ASSERT(!ec); 3388e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project CharacterIterator it(range.get()); 3398e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project it.advance(index - 1); 340635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project Node* endContainer = it.range()->endContainer(ec); 341635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project ASSERT(!ec); 342635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project int endOffset = it.range()->endOffset(ec); 343635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project ASSERT(!ec); 34481bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch return VisiblePosition(Position(endContainer, endOffset, Position::PositionIsOffsetInAnchor), UPSTREAM); 3458e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 3468e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 347d0147a863b872ecaa451ab0dce2a348760e99e2cBen Murdochint RenderTextControl::indexForVisiblePosition(HTMLElement* innerTextElement, const VisiblePosition& pos) 3488e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 3498e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project Position indexPosition = pos.deepEquivalent(); 350d0147a863b872ecaa451ab0dce2a348760e99e2cBen Murdoch if (!RenderTextControl::isSelectableElement(innerTextElement, indexPosition.deprecatedNode())) 3518e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return 0; 3528e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ExceptionCode ec = 0; 353d0147a863b872ecaa451ab0dce2a348760e99e2cBen Murdoch RefPtr<Range> range = Range::create(indexPosition.document()); 354d0147a863b872ecaa451ab0dce2a348760e99e2cBen Murdoch range->setStart(innerTextElement, 0, ec); 355635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project ASSERT(!ec); 35681bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch range->setEnd(indexPosition.deprecatedNode(), indexPosition.deprecatedEditingOffset(), ec); 357635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project ASSERT(!ec); 3588e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return TextIterator::rangeLength(range.get()); 3598e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 3608e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 3618e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectvoid RenderTextControl::subtreeHasChanged() 3628e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 363643ca7872b450ea4efacab6188849e5aac2ba161Steve Block m_lastChangeWasUserEdit = true; 3648e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 3658e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 3668e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source ProjectString RenderTextControl::finishText(Vector<UChar>& result) const 3678e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 3688e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // Remove one trailing newline; there's always one that's collapsed out by rendering. 3698e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project size_t size = result.size(); 3708e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (size && result[size - 1] == '\n') 3718e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project result.shrink(--size); 3728e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 3738e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return String::adopt(result); 3748e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 3758e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 3768e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source ProjectString RenderTextControl::text() 3778e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 3788e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (!m_innerText) 3798e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return ""; 3808e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 3818e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project Vector<UChar> result; 3828e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 3838e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project for (Node* n = m_innerText.get(); n; n = n->traverseNextNode(m_innerText.get())) { 384635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (n->hasTagName(brTag)) 385635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project result.append(&newlineCharacter, 1); 386635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project else if (n->isTextNode()) { 3870bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch String data = static_cast<Text*>(n)->data(); 3880bf48ef3be53ddaa52bbead65dfd75bf90e7a2b5Ben Murdoch result.append(data.characters(), data.length()); 3898e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 3908e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 3918e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 3928e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return finishText(result); 3938e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 3948e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 3958e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Projectstatic void getNextSoftBreak(RootInlineBox*& line, Node*& breakNode, unsigned& breakOffset) 3968e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 3978e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project RootInlineBox* next; 3988e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project for (; line; line = next) { 3998e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project next = line->nextRootBox(); 4008e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (next && !line->endsWithBreak()) { 4018e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project ASSERT(line->lineBreakObj()); 4028e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project breakNode = line->lineBreakObj()->node(); 4038e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project breakOffset = line->lineBreakPos(); 4048e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project line = next; 4058e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return; 4068e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 4078e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 4088e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project breakNode = 0; 4095f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian breakOffset = 0; 4108e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 4118e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 4128e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source ProjectString RenderTextControl::textWithHardLineBreaks() 4138e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 4148e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (!m_innerText) 4158e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return ""; 4168e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 4175ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen RenderBlock* renderer = toRenderBlock(m_innerText->renderer()); 4188e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (!renderer) 4198e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return ""; 4208e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 4218e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project Node* breakNode; 4228e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project unsigned breakOffset; 4235ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen RootInlineBox* line = renderer->firstRootBox(); 4245ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen if (!line) 4255ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen return ""; 4265ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 4278e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project getNextSoftBreak(line, breakNode, breakOffset); 4288e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 4298e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project Vector<UChar> result; 4308e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 4315ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen for (Node* n = m_innerText->firstChild(); n; n = n->traverseNextNode(m_innerText.get())) { 4328e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (n->hasTagName(brTag)) 4338e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project result.append(&newlineCharacter, 1); 4348e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project else if (n->isTextNode()) { 4358e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project Text* text = static_cast<Text*>(n); 4368e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project String data = text->data(); 4378e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project unsigned length = data.length(); 4388e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project unsigned position = 0; 4398e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project while (breakNode == n && breakOffset <= length) { 4408e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (breakOffset > position) { 4418e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project result.append(data.characters() + position, breakOffset - position); 4428e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project position = breakOffset; 4438e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project result.append(&newlineCharacter, 1); 4448e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 4458e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project getNextSoftBreak(line, breakNode, breakOffset); 4468e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 4478e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project result.append(data.characters() + position, length - position); 4488e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 4498e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project while (breakNode == n) 4508e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project getNextSoftBreak(line, breakNode, breakOffset); 4518e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 4528e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 4538e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project return finishText(result); 4548e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 4558e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 456635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Projectint RenderTextControl::scrollbarThickness() const 4578e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 458635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project // FIXME: We should get the size of the scrollbar from the RenderTheme instead. 459635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project return ScrollbarTheme::nativeTheme()->scrollbarThickness(); 460635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project} 4618e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 462bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsenvoid RenderTextControl::computeLogicalHeight() 463635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project{ 464635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project setHeight(m_innerText->renderBox()->borderTop() + m_innerText->renderBox()->borderBottom() + 465635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project m_innerText->renderBox()->paddingTop() + m_innerText->renderBox()->paddingBottom() + 466635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project m_innerText->renderBox()->marginTop() + m_innerText->renderBox()->marginBottom()); 4678e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 468a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch adjustControlHeightBasedOnLineHeight(m_innerText->renderBox()->lineHeight(true, HorizontalLine, PositionOfInteriorLineBoxes)); 46921939df44de1705786c545cd1bf519d47250322dBen Murdoch setHeight(height() + borderAndPaddingHeight()); 4708e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 4718e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project // We are able to have a horizontal scrollbar if the overflow style is scroll, or if its auto and there's no word wrap. 4728f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian if (style()->overflowX() == OSCROLL || (style()->overflowX() == OAUTO && m_innerText->renderer()->style()->wordWrap() == NormalWordWrap)) 473635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project setHeight(height() + scrollbarThickness()); 4748e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 475bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen RenderBlock::computeLogicalHeight(); 4768e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 4778e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 4788f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qianvoid RenderTextControl::hitInnerTextElement(HitTestResult& result, int xPos, int yPos, int tx, int ty) 4798e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 480635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project result.setInnerNode(m_innerText.get()); 4818f72e70a9fd78eec56623b3a62e68f16b7b27e28Feng Qian result.setInnerNonSharedNode(m_innerText.get()); 482635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project result.setLocalPoint(IntPoint(xPos - tx - x() - m_innerText->renderBox()->x(), 483635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project yPos - ty - y() - m_innerText->renderBox()->y())); 4848e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 4858e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 486635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Projectvoid RenderTextControl::forwardEvent(Event* event) 4878e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 488635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (event->type() == eventNames().blurEvent || event->type() == eventNames().focusEvent) 489635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project return; 490635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project m_innerText->defaultEventHandler(event); 4918e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 4928e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 493692e5dbf12901edacf14812a6fae25462920af42Steve Blockstatic const char* fontFamiliesWithInvalidCharWidth[] = { 494692e5dbf12901edacf14812a6fae25462920af42Steve Block "American Typewriter", 495692e5dbf12901edacf14812a6fae25462920af42Steve Block "Arial Hebrew", 496692e5dbf12901edacf14812a6fae25462920af42Steve Block "Chalkboard", 497692e5dbf12901edacf14812a6fae25462920af42Steve Block "Cochin", 498692e5dbf12901edacf14812a6fae25462920af42Steve Block "Corsiva Hebrew", 499692e5dbf12901edacf14812a6fae25462920af42Steve Block "Courier", 500692e5dbf12901edacf14812a6fae25462920af42Steve Block "Euphemia UCAS", 501692e5dbf12901edacf14812a6fae25462920af42Steve Block "Geneva", 502692e5dbf12901edacf14812a6fae25462920af42Steve Block "Gill Sans", 503692e5dbf12901edacf14812a6fae25462920af42Steve Block "Hei", 504692e5dbf12901edacf14812a6fae25462920af42Steve Block "Helvetica", 505692e5dbf12901edacf14812a6fae25462920af42Steve Block "Hoefler Text", 506692e5dbf12901edacf14812a6fae25462920af42Steve Block "InaiMathi", 507692e5dbf12901edacf14812a6fae25462920af42Steve Block "Kai", 508692e5dbf12901edacf14812a6fae25462920af42Steve Block "Lucida Grande", 509692e5dbf12901edacf14812a6fae25462920af42Steve Block "Marker Felt", 510692e5dbf12901edacf14812a6fae25462920af42Steve Block "Monaco", 511692e5dbf12901edacf14812a6fae25462920af42Steve Block "Mshtakan", 512692e5dbf12901edacf14812a6fae25462920af42Steve Block "New Peninim MT", 513692e5dbf12901edacf14812a6fae25462920af42Steve Block "Osaka", 514692e5dbf12901edacf14812a6fae25462920af42Steve Block "Raanana", 515692e5dbf12901edacf14812a6fae25462920af42Steve Block "STHeiti", 516692e5dbf12901edacf14812a6fae25462920af42Steve Block "Symbol", 517692e5dbf12901edacf14812a6fae25462920af42Steve Block "Times", 518692e5dbf12901edacf14812a6fae25462920af42Steve Block "Apple Braille", 519692e5dbf12901edacf14812a6fae25462920af42Steve Block "Apple LiGothic", 520692e5dbf12901edacf14812a6fae25462920af42Steve Block "Apple LiSung", 521692e5dbf12901edacf14812a6fae25462920af42Steve Block "Apple Symbols", 522692e5dbf12901edacf14812a6fae25462920af42Steve Block "AppleGothic", 523692e5dbf12901edacf14812a6fae25462920af42Steve Block "AppleMyungjo", 524692e5dbf12901edacf14812a6fae25462920af42Steve Block "#GungSeo", 525692e5dbf12901edacf14812a6fae25462920af42Steve Block "#HeadLineA", 526692e5dbf12901edacf14812a6fae25462920af42Steve Block "#PCMyungjo", 527692e5dbf12901edacf14812a6fae25462920af42Steve Block "#PilGi", 528692e5dbf12901edacf14812a6fae25462920af42Steve Block}; 529692e5dbf12901edacf14812a6fae25462920af42Steve Block 530692e5dbf12901edacf14812a6fae25462920af42Steve Block// For font families where any of the fonts don't have a valid entry in the OS/2 table 531692e5dbf12901edacf14812a6fae25462920af42Steve Block// for avgCharWidth, fallback to the legacy webkit behavior of getting the avgCharWidth 532692e5dbf12901edacf14812a6fae25462920af42Steve Block// from the width of a '0'. This only seems to apply to a fixed number of Mac fonts, 533692e5dbf12901edacf14812a6fae25462920af42Steve Block// but, in order to get similar rendering across platforms, we do this check for 534692e5dbf12901edacf14812a6fae25462920af42Steve Block// all platforms. 535692e5dbf12901edacf14812a6fae25462920af42Steve Blockbool RenderTextControl::hasValidAvgCharWidth(AtomicString family) 536692e5dbf12901edacf14812a6fae25462920af42Steve Block{ 537692e5dbf12901edacf14812a6fae25462920af42Steve Block static HashSet<AtomicString>* fontFamiliesWithInvalidCharWidthMap = 0; 5384576aa36e9a9671459299c7963ac95aa94beaea9Shimeng (Simon) Wang 539692e5dbf12901edacf14812a6fae25462920af42Steve Block if (!fontFamiliesWithInvalidCharWidthMap) { 540692e5dbf12901edacf14812a6fae25462920af42Steve Block fontFamiliesWithInvalidCharWidthMap = new HashSet<AtomicString>; 5414576aa36e9a9671459299c7963ac95aa94beaea9Shimeng (Simon) Wang 5424576aa36e9a9671459299c7963ac95aa94beaea9Shimeng (Simon) Wang for (size_t i = 0; i < WTF_ARRAY_LENGTH(fontFamiliesWithInvalidCharWidth); ++i) 543692e5dbf12901edacf14812a6fae25462920af42Steve Block fontFamiliesWithInvalidCharWidthMap->add(AtomicString(fontFamiliesWithInvalidCharWidth[i])); 544692e5dbf12901edacf14812a6fae25462920af42Steve Block } 545692e5dbf12901edacf14812a6fae25462920af42Steve Block 546692e5dbf12901edacf14812a6fae25462920af42Steve Block return !fontFamiliesWithInvalidCharWidthMap->contains(family); 547692e5dbf12901edacf14812a6fae25462920af42Steve Block} 548692e5dbf12901edacf14812a6fae25462920af42Steve Block 549692e5dbf12901edacf14812a6fae25462920af42Steve Blockfloat RenderTextControl::getAvgCharWidth(AtomicString family) 550692e5dbf12901edacf14812a6fae25462920af42Steve Block{ 551692e5dbf12901edacf14812a6fae25462920af42Steve Block if (hasValidAvgCharWidth(family)) 552692e5dbf12901edacf14812a6fae25462920af42Steve Block return roundf(style()->font().primaryFont()->avgCharWidth()); 553692e5dbf12901edacf14812a6fae25462920af42Steve Block 554692e5dbf12901edacf14812a6fae25462920af42Steve Block const UChar ch = '0'; 55581bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch return style()->font().width(TextRun(&ch, 1, false, 0, 0, TextRun::AllowTrailingExpansion, false)); 556692e5dbf12901edacf14812a6fae25462920af42Steve Block} 557692e5dbf12901edacf14812a6fae25462920af42Steve Block 558692e5dbf12901edacf14812a6fae25462920af42Steve Blockfloat RenderTextControl::scaleEmToUnits(int x) const 559692e5dbf12901edacf14812a6fae25462920af42Steve Block{ 560692e5dbf12901edacf14812a6fae25462920af42Steve Block // This matches the unitsPerEm value for MS Shell Dlg and Courier New from the "head" font table. 561692e5dbf12901edacf14812a6fae25462920af42Steve Block float unitsPerEm = 2048.0f; 562692e5dbf12901edacf14812a6fae25462920af42Steve Block return roundf(style()->font().size() * x / unitsPerEm); 563692e5dbf12901edacf14812a6fae25462920af42Steve Block} 564692e5dbf12901edacf14812a6fae25462920af42Steve Block 565bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsenvoid RenderTextControl::computePreferredLogicalWidths() 5668e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 567bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen ASSERT(preferredLogicalWidthsDirty()); 5688e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 569bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen m_minPreferredLogicalWidth = 0; 570bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen m_maxPreferredLogicalWidth = 0; 5718e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 5728e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (style()->width().isFixed() && style()->width().value() > 0) 573bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen m_minPreferredLogicalWidth = m_maxPreferredLogicalWidth = computeContentBoxLogicalWidth(style()->width().value()); 5748e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project else { 5755f1ab04193ad0130ca8204aadaceae083aca9881Feng Qian // Use average character width. Matches IE. 576692e5dbf12901edacf14812a6fae25462920af42Steve Block AtomicString family = style()->font().family().family(); 577bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen m_maxPreferredLogicalWidth = preferredContentWidth(getAvgCharWidth(family)) + m_innerText->renderBox()->paddingLeft() + m_innerText->renderBox()->paddingRight(); 5788e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 5798e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 5808e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (style()->minWidth().isFixed() && style()->minWidth().value() > 0) { 581bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen m_maxPreferredLogicalWidth = max(m_maxPreferredLogicalWidth, computeContentBoxLogicalWidth(style()->minWidth().value())); 582bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen m_minPreferredLogicalWidth = max(m_minPreferredLogicalWidth, computeContentBoxLogicalWidth(style()->minWidth().value())); 5838e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } else if (style()->width().isPercent() || (style()->width().isAuto() && style()->height().isPercent())) 584bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen m_minPreferredLogicalWidth = 0; 5858e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project else 586bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen m_minPreferredLogicalWidth = m_maxPreferredLogicalWidth; 5878e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 5888e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project if (style()->maxWidth().isFixed() && style()->maxWidth().value() != undefinedLength) { 589bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen m_maxPreferredLogicalWidth = min(m_maxPreferredLogicalWidth, computeContentBoxLogicalWidth(style()->maxWidth().value())); 590bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen m_minPreferredLogicalWidth = min(m_minPreferredLogicalWidth, computeContentBoxLogicalWidth(style()->maxWidth().value())); 5918e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 5928e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 59321939df44de1705786c545cd1bf519d47250322dBen Murdoch int toAdd = borderAndPaddingWidth(); 5948e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 595bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen m_minPreferredLogicalWidth += toAdd; 596bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen m_maxPreferredLogicalWidth += toAdd; 5978e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 598bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen setPreferredLogicalWidthsDirty(false); 5998e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 6008e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 601635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Projectvoid RenderTextControl::selectionChanged(bool userTriggered) 6028e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 603635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project cacheSelection(selectionStart(), selectionEnd()); 604635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project 605545e470e52f0ac6a3a072bf559c796b42c6066b6Ben Murdoch if (Frame* frame = this->frame()) { 606635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project if (frame->selection()->isRange() && userTriggered) 607231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block node()->dispatchEvent(Event::create(eventNames().selectEvent, true, false)); 6088e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project } 6098e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 6108e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 611d0825bca7fe65beaee391d30da42e937db621564Steve Blockvoid RenderTextControl::addFocusRingRects(Vector<IntRect>& rects, int tx, int ty) 6128e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 613d0825bca7fe65beaee391d30da42e937db621564Steve Block if (width() && height()) 614d0825bca7fe65beaee391d30da42e937db621564Steve Block rects.append(IntRect(tx, ty, width(), height())); 6158e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 6168e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 617635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source ProjectHTMLElement* RenderTextControl::innerTextElement() const 6188e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project{ 619635860845790a19bf50bbc51ba8fb66a96dde068The Android Open Source Project return m_innerText.get(); 6208e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} 6218e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project 622231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Blockvoid RenderTextControl::updatePlaceholderVisibility(bool placeholderShouldBeVisible, bool placeholderValueChanged) 623231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block{ 624231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block bool oldPlaceholderVisible = m_placeholderVisible; 625231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block m_placeholderVisible = placeholderShouldBeVisible; 6266b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner if (oldPlaceholderVisible != m_placeholderVisible || placeholderValueChanged) 6276b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner repaint(); 6286b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner} 629231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 6306b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brennervoid RenderTextControl::paintPlaceholder(PaintInfo& paintInfo, int tx, int ty) 6316b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner{ 6326b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner if (style()->visibility() != VISIBLE) 6336b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner return; 6346b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner 6356b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner IntRect clipRect(tx + borderLeft(), ty + borderTop(), width() - borderLeft() - borderRight(), height() - borderBottom() - borderTop()); 6366b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner if (clipRect.isEmpty()) 6376b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner return; 6386b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner 6396b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner paintInfo.context->save(); 6406b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner 6416b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner paintInfo.context->clip(clipRect); 6426b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner 6436b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner RefPtr<RenderStyle> placeholderStyle = getCachedPseudoStyle(INPUT_PLACEHOLDER); 6446b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner if (!placeholderStyle) 6456b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner placeholderStyle = style(); 6466b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner 6476b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner paintInfo.context->setFillColor(placeholderStyle->visitedDependentColor(CSSPropertyColor), placeholderStyle->colorSpace()); 6486b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner 6496b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner String placeholderText = static_cast<HTMLTextFormControlElement*>(node())->strippedPlaceholder(); 65081bc750723a18f21cd17d1b173cd2a4dda9cea6eBen Murdoch TextRun textRun(placeholderText.characters(), placeholderText.length(), false, 0, 0, TextRun::AllowTrailingExpansion, !placeholderStyle->isLeftToRightDirection(), placeholderStyle->unicodeBidi() == Override); 6516b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner 6526b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner RenderBox* textRenderer = innerTextElement() ? innerTextElement()->renderBox() : 0; 6536b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner if (textRenderer) { 6546b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner IntPoint textPoint; 6552fc2651226baac27029e38c9d6ef883fa32084dbSteve Block textPoint.setY(ty + textBlockInsetTop() + placeholderStyle->fontMetrics().ascent()); 6566b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner if (placeholderStyle->isLeftToRightDirection()) 6576b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner textPoint.setX(tx + textBlockInsetLeft()); 6586b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner else 6596b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner textPoint.setX(tx + width() - textBlockInsetRight() - style()->font().width(textRun)); 6606b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner 6616b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner paintInfo.context->drawBidiText(placeholderStyle->font(), textRun, textPoint); 662231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block } 6636b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner paintInfo.context->restore(); 6646b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner} 6656b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner 6666b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brennervoid RenderTextControl::paintObject(PaintInfo& paintInfo, int tx, int ty) 6676b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner{ 6686b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner if (m_placeholderVisible && paintInfo.phase == PaintPhaseForeground) 6696b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner paintPlaceholder(paintInfo, tx, ty); 6706b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner 6716b70adc33054f8aee8c54d0f460458a9df11b8a5Russell Brenner RenderBlock::paintObject(paintInfo, tx, ty); 672231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block} 673231d4e3152a9c27a73b6ac7badbe6be673aa3ddfSteve Block 6748e35f3cfc7fba1d1c829dc557ebad6409cbe16a2The Android Open Source Project} // namespace WebCore 675