| Index: Source/WebCore/html/HTMLSelectElement.cpp
|
| diff --git a/Source/WebCore/html/HTMLSelectElement.cpp b/Source/WebCore/html/HTMLSelectElement.cpp
|
| index e51408a387b6da97b5073a57cd3d6d61c4df28f7..c8d7da027f3e47e3702880d19b83eb25c89e89bb 100644
|
| --- a/Source/WebCore/html/HTMLSelectElement.cpp
|
| +++ b/Source/WebCore/html/HTMLSelectElement.cpp
|
| @@ -51,6 +51,7 @@
|
| #include "RenderListBox.h"
|
| #include "RenderMenuList.h"
|
| #include "RenderTheme.h"
|
| + #include "StyleResolver.h"
|
| #include "ScriptEventListener.h"
|
| #include "SpatialNavigation.h"
|
| #include <wtf/text/StringBuilder.h>
|
| @@ -674,9 +675,13 @@ void HTMLSelectElement::scrollToSelection()
|
| {
|
| if (usesMenuList())
|
| return;
|
| -
|
| - if (RenderObject* renderer = this->renderer())
|
| - toRenderListBox(renderer)->selectionChanged();
|
| + int listIndex = activeSelectionEndListIndex();
|
| + const Vector<HTMLElement*>& items = listItems();
|
| + int listSize = static_cast<int>(items.size());
|
| + if (listIndex < 0 || listIndex >= listSize)
|
| + return;
|
| + Element* option = listItems()[listIndex];
|
| + option->scrollIntoViewIfNeeded(false);
|
| }
|
|
|
| void HTMLSelectElement::setOptionsChangedOnRenderer()
|
| @@ -684,8 +689,8 @@ void HTMLSelectElement::setOptionsChangedOnRenderer()
|
| if (RenderObject* renderer = this->renderer()) {
|
| if (usesMenuList())
|
| toRenderMenuList(renderer)->setOptionsChanged(true);
|
| - else
|
| - toRenderListBox(renderer)->setOptionsChanged(true);
|
| +// else
|
| +// scrollToSelection();
|
| }
|
| }
|
|
|
| @@ -859,8 +864,6 @@ void HTMLSelectElement::selectOption(int optionIndex, SelectOptionFlags flags)
|
| if (RenderObject* renderer = this->renderer()) {
|
| if (usesMenuList())
|
| toRenderMenuList(renderer)->didSetSelectedIndex(listIndex);
|
| - else if (renderer->isListBox())
|
| - toRenderListBox(renderer)->selectionChanged();
|
| }
|
| }
|
|
|
| @@ -1284,6 +1287,22 @@ void HTMLSelectElement::updateSelectedState(int listIndex, bool multi, bool shif
|
| updateListBoxSelection(!multiSelect);
|
| }
|
|
|
| +int HTMLSelectElement::listIndexForEvent(Event* event)
|
| +{
|
| + const Vector<HTMLElement*>& items = this->listItems();
|
| + for (Node* node = event->target()->toNode(); node; node = node->parentOrShadowHostNode()) {
|
| + if (node->isElementNode() && (toElement(node)->hasTagName(optionTag) || toElement(node)->hasTagName(optgroupTag))) {
|
| + size_t length = items.size();
|
| + for (size_t i = 0; i < length; ++i) {
|
| + if (items[i] == node) {
|
| + return i;
|
| + }
|
| + }
|
| + }
|
| + }
|
| + return -1;
|
| +}
|
| +
|
| void HTMLSelectElement::listBoxDefaultEventHandler(Event* event)
|
| {
|
| const Vector<HTMLElement*>& listItems = this->listItems();
|
| @@ -1294,10 +1313,8 @@ void HTMLSelectElement::listBoxDefaultEventHandler(Event* event)
|
| if (!renderer())
|
| return;
|
|
|
| - // Convert to coords relative to the list box if needed.
|
| MouseEvent* mouseEvent = static_cast<MouseEvent*>(event);
|
| - IntPoint localOffset = roundedIntPoint(renderer()->absoluteToLocal(mouseEvent->absoluteLocation(), UseTransforms));
|
| - int listIndex = toRenderListBox(renderer())->listIndexAtOffset(toIntSize(localOffset));
|
| + int listIndex = listIndexForEvent(event);
|
| if (listIndex >= 0) {
|
| if (!isDisabledFormControl()) {
|
| #if OS(DARWIN)
|
| @@ -1311,13 +1328,12 @@ void HTMLSelectElement::listBoxDefaultEventHandler(Event* event)
|
|
|
| event->setDefaultHandled();
|
| }
|
| - } else if (event->type() == eventNames().mousemoveEvent && event->isMouseEvent() && !toRenderBox(renderer())->canBeScrolledAndHasScrollableArea()) {
|
| + } else if (event->type() == eventNames().mousemoveEvent && event->isMouseEvent()) {
|
| MouseEvent* mouseEvent = static_cast<MouseEvent*>(event);
|
| if (mouseEvent->button() != LeftButton || !mouseEvent->buttonDown())
|
| return;
|
|
|
| - IntPoint localOffset = roundedIntPoint(renderer()->absoluteToLocal(mouseEvent->absoluteLocation(), UseTransforms));
|
| - int listIndex = toRenderListBox(renderer())->listIndexAtOffset(toIntSize(localOffset));
|
| + int listIndex = listIndexForEvent(event);
|
| if (listIndex >= 0) {
|
| if (!isDisabledFormControl()) {
|
| if (m_multiple) {
|
| @@ -1335,12 +1351,9 @@ void HTMLSelectElement::listBoxDefaultEventHandler(Event* event)
|
| }
|
| event->setDefaultHandled();
|
| }
|
| - } else if (event->type() == eventNames().mouseupEvent && event->isMouseEvent() && static_cast<MouseEvent*>(event)->button() == LeftButton && document()->frame()->eventHandler()->autoscrollRenderer() != renderer()) {
|
| - // This makes sure we fire dispatchFormControlChangeEvent for a single
|
| - // click. For drag selection, onChange will fire when the autoscroll
|
| - // timer stops.
|
| + } else if (event->type() == eventNames().mouseupEvent && event->isMouseEvent() && static_cast<MouseEvent*>(event)->button() == LeftButton)
|
| listBoxOnChange();
|
| - } else if (event->type() == eventNames().keydownEvent) {
|
| + else if (event->type() == eventNames().keydownEvent) {
|
| if (!event->isKeyboardEvent())
|
| return;
|
| const String& keyIdentifier = static_cast<KeyboardEvent*>(event)->keyIdentifier();
|
| @@ -1414,7 +1427,7 @@ void HTMLSelectElement::listBoxDefaultEventHandler(Event* event)
|
| setActiveSelectionAnchorIndex(m_activeSelectionEndIndex);
|
| }
|
|
|
| - toRenderListBox(renderer())->scrollToRevealElementAtListIndex(endIndex);
|
| + listItems[endIndex]->scrollIntoViewIfNeeded(false);
|
| if (selectNewItem) {
|
| updateListBoxSelection(deselectOthers);
|
| listBoxOnChange();
|
| @@ -1561,4 +1574,14 @@ unsigned HTMLSelectElement::length() const
|
| return options;
|
| }
|
|
|
| +void HTMLSelectElement::dispatchFormControlChangeEvent()
|
| +{
|
| + if (renderer() && renderer()->isListBox()) {
|
| + AXObjectCache* cache = document()->existingAXObjectCache();
|
| + if (cache)
|
| + cache->selectedChildrenChanged(renderer());
|
| + }
|
| + HTMLFormControlElement::dispatchChangeEvent();
|
| +}
|
| +
|
| } // namespace
|
|
|