15c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)/*
25c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * Copyright (C) 2006, 2007, 2008 Apple Inc. All rights reserved.
35c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * Copyright (C) 2008 Nokia Corporation and/or its subsidiary(-ies)
45c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * Copyright (C) 2009 Igalia S.L.
55c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) *
65c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * Redistribution and use in source and binary forms, with or without
75c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * modification, are permitted provided that the following conditions
85c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * are met:
95c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * 1. Redistributions of source code must retain the above copyright
105c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) *    notice, this list of conditions and the following disclaimer.
115c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * 2. Redistributions in binary form must reproduce the above copyright
125c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) *    notice, this list of conditions and the following disclaimer in the
135c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) *    documentation and/or other materials provided with the distribution.
145c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) *
155c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY
165c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
175c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
185c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL APPLE COMPUTER, INC. OR
195c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
205c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
215c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
225c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
235c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
245c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
2502772c6a72f1ee0b226341a4f4439970c29fc861Ben Murdoch * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
265c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles) */
275c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
285c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)#include "config.h"
2953e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)#include "core/editing/Editor.h"
305c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
315c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)#include "CSSPropertyNames.h"
325c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)#include "CSSValueKeywords.h"
335c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)#include "HTMLNames.h"
341fad5ca6c42d689812b66fc493992aa6d747a6fbBen Murdoch#include "bindings/v8/ExceptionState.h"
35df95704c49daea886ddad70775bda23618d6274dBen Murdoch#include "bindings/v8/ExceptionStatePlaceholder.h"
3653e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)#include "core/css/CSSValueList.h"
3753e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)#include "core/css/StylePropertySet.h"
3853e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)#include "core/dom/DocumentFragment.h"
3906f816c7c76bc45a15e452ade8a34e8af077693eTorne (Richard Coles)#include "core/events/Event.h"
4053e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)#include "core/editing/CreateLinkCommand.h"
4153e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)#include "core/editing/FormatBlockCommand.h"
4253e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)#include "core/editing/IndentOutdentCommand.h"
4353e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)#include "core/editing/InsertListCommand.h"
4453e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)#include "core/editing/ReplaceSelectionCommand.h"
451e202183a5dc46166763171984b285173f8585e5Torne (Richard Coles)#include "core/editing/SpellChecker.h"
4653e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)#include "core/editing/TypingCommand.h"
4753e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)#include "core/editing/UnlinkCommand.h"
4853e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)#include "core/editing/markup.h"
4953e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)#include "core/html/HTMLFontElement.h"
5053e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)#include "core/html/HTMLHRElement.h"
5153e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)#include "core/html/HTMLImageElement.h"
5253e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)#include "core/page/Chrome.h"
5353e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)#include "core/page/EditorClient.h"
5453e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)#include "core/page/EventHandler.h"
551e202183a5dc46166763171984b285173f8585e5Torne (Richard Coles)#include "core/frame/Frame.h"
561e202183a5dc46166763171984b285173f8585e5Torne (Richard Coles)#include "core/frame/FrameView.h"
5753e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)#include "core/page/Page.h"
58e08f70592b3fc0d5e68b9b914c9196e813720070Torne (Richard Coles)#include "core/frame/Settings.h"
5953e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)#include "core/platform/Pasteboard.h"
6053e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)#include "core/rendering/RenderBox.h"
6151b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)#include "platform/KillRing.h"
62a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)#include "platform/scroll/Scrollbar.h"
63e69819bd8e388ea4ad1636a19aa6b2eed4952191Ben Murdoch#include "wtf/text/AtomicString.h"
645c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
655c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)namespace WebCore {
665c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
675c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)using namespace HTMLNames;
685c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
695c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)class EditorInternalCommand {
705c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)public:
71c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    bool (*execute)(Frame&, Event*, EditorCommandSource, const String&);
725c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    bool (*isSupportedFromDOM)(Frame*);
73c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    bool (*isEnabled)(Frame&, Event*, EditorCommandSource);
74c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    TriState (*state)(Frame&, Event*);
75c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    String (*value)(Frame&, Event*);
765c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    bool isTextInsertion;
775c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    bool allowExecutionWhenDisabled;
785c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)};
795c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
805c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)typedef HashMap<String, const EditorInternalCommand*, CaseFoldingHash> CommandMap;
815c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
825c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)static const bool notTextInsertion = false;
835c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)static const bool isTextInsertion = true;
845c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
855c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)static const bool allowExecutionWhenDisabled = true;
865c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)static const bool doNotAllowExecutionWhenDisabled = false;
875c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
885c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)// Related to Editor::selectionForCommand.
895c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)// Certain operations continue to use the target control's selection even if the event handler
905c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)// already moved the selection outside of the text control.
91c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static Frame* targetFrame(Frame& frame, Event* event)
925c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
935c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    if (!event)
94c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)        return &frame;
955c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    Node* node = event->target()->toNode();
965c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    if (!node)
97c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)        return &frame;
988abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    return node->document().frame();
995c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
1005c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
101c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool applyCommandToFrame(Frame& frame, EditorCommandSource source, EditAction action, StylePropertySet* style)
1025c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
1035c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // FIXME: We don't call shouldApplyStyle when the source is DOM; is there a good reason for that?
1045c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    switch (source) {
1055c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    case CommandFromMenuOrKeyBinding:
106c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)        frame.editor().applyStyleToSelection(style, action);
1075c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return true;
1085c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    case CommandFromDOM:
1095c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    case CommandFromDOMWithUserInterface:
110c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)        frame.editor().applyStyle(style);
1115c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return true;
1125c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    }
1135c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    ASSERT_NOT_REACHED();
1145c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return false;
1155c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
1165c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
117c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeApplyStyle(Frame& frame, EditorCommandSource source, EditAction action, CSSPropertyID propertyID, const String& propertyValue)
1185c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
11993ac45cfc74041c8ae536ce58a9534d46db2024eTorne (Richard Coles)    RefPtr<MutableStylePropertySet> style = MutableStylePropertySet::create();
1205c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    style->setProperty(propertyID, propertyValue);
1215c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return applyCommandToFrame(frame, source, action, style.get());
1225c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
1235c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
124c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeApplyStyle(Frame& frame, EditorCommandSource source, EditAction action, CSSPropertyID propertyID, CSSValueID propertyValue)
1255c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
12693ac45cfc74041c8ae536ce58a9534d46db2024eTorne (Richard Coles)    RefPtr<MutableStylePropertySet> style = MutableStylePropertySet::create();
1275c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    style->setProperty(propertyID, propertyValue);
1285c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return applyCommandToFrame(frame, source, action, style.get());
1295c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
1305c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1315c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)// FIXME: executeToggleStyleInList does not handle complicated cases such as <b><u>hello</u>world</b> properly.
1325c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)//        This function must use Editor::selectionHasStyle to determine the current style but we cannot fix this
1335c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)//        until https://bugs.webkit.org/show_bug.cgi?id=27818 is resolved.
134c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeToggleStyleInList(Frame& frame, EditorCommandSource source, EditAction action, CSSPropertyID propertyID, CSSValue* value)
1355c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
1368abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    RefPtr<EditingStyle> selectionStyle = EditingStyle::styleAtSelectionStart(frame.selection().selection());
1375c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    if (!selectionStyle || !selectionStyle->style())
1385c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return false;
1395c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1405c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    RefPtr<CSSValue> selectedCSSValue = selectionStyle->style()->getPropertyCSSValue(propertyID);
1413c9e4aeaee9f9b0a9a814da07bcb33319c7ea363Ben Murdoch    String newStyle("none");
1425c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    if (selectedCSSValue->isValueList()) {
1433c9e4aeaee9f9b0a9a814da07bcb33319c7ea363Ben Murdoch        RefPtr<CSSValueList> selectedCSSValueList = toCSSValueList(selectedCSSValue.get());
1445c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        if (!selectedCSSValueList->removeAll(value))
1455c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)            selectedCSSValueList->append(value);
1465c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        if (selectedCSSValueList->length())
1475c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)            newStyle = selectedCSSValueList->cssText();
1485c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1495c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    } else if (selectedCSSValue->cssText() == "none")
1505c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        newStyle = value->cssText();
1515c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1525c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // FIXME: We shouldn't be having to convert new style into text.  We should have setPropertyCSSValue.
15393ac45cfc74041c8ae536ce58a9534d46db2024eTorne (Richard Coles)    RefPtr<MutableStylePropertySet> newMutableStyle = MutableStylePropertySet::create();
1545c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    newMutableStyle->setProperty(propertyID, newStyle);
1555c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return applyCommandToFrame(frame, source, action, newMutableStyle.get());
1565c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
1575c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
158c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeToggleStyle(Frame& frame, EditorCommandSource source, EditAction action, CSSPropertyID propertyID, const char* offValue, const char* onValue)
1595c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
1605c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // Style is considered present when
1615c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // Mac: present at the beginning of selection
1625c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // other: present throughout the selection
1635c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1645c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    bool styleIsPresent;
165c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    if (frame.editor().behavior().shouldToggleStyleBasedOnStartOfSelection())
166c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)        styleIsPresent = frame.editor().selectionStartHasStyle(propertyID, onValue);
1675c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    else
168c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)        styleIsPresent = frame.editor().selectionHasStyle(propertyID, onValue) == TrueTriState;
1695c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1705c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    RefPtr<EditingStyle> style = EditingStyle::create(propertyID, styleIsPresent ? offValue : onValue);
1715c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return applyCommandToFrame(frame, source, action, style->style());
1725c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
1735c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
174c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeApplyParagraphStyle(Frame& frame, EditorCommandSource source, EditAction action, CSSPropertyID propertyID, const String& propertyValue)
1755c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
17693ac45cfc74041c8ae536ce58a9534d46db2024eTorne (Richard Coles)    RefPtr<MutableStylePropertySet> style = MutableStylePropertySet::create();
1775c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    style->setProperty(propertyID, propertyValue);
1785c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // FIXME: We don't call shouldApplyStyle when the source is DOM; is there a good reason for that?
1795c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    switch (source) {
1805c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    case CommandFromMenuOrKeyBinding:
181c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)        frame.editor().applyParagraphStyleToSelection(style.get(), action);
1825c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return true;
1835c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    case CommandFromDOM:
1845c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    case CommandFromDOMWithUserInterface:
185c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)        frame.editor().applyParagraphStyle(style.get());
1865c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return true;
1875c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    }
1885c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    ASSERT_NOT_REACHED();
1895c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return false;
1905c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
1915c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
192c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeInsertFragment(Frame& frame, PassRefPtr<DocumentFragment> fragment)
1935c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
1948abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    ASSERT(frame.document());
1958abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    ReplaceSelectionCommand::create(*frame.document(), fragment, ReplaceSelectionCommand::PreventNesting, EditActionUnspecified)->apply();
1965c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
1975c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
1985c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
199c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeInsertNode(Frame& frame, PassRefPtr<Node> content)
2005c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
2018abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    ASSERT(frame.document());
2028abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    RefPtr<DocumentFragment> fragment = DocumentFragment::create(*frame.document());
20351b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    TrackExceptionState exceptionState;
20451b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    fragment->appendChild(content, exceptionState);
20551b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    if (exceptionState.hadException())
2065c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return false;
2075c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return executeInsertFragment(frame, fragment.release());
2085c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
2095c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
210c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool expandSelectionToGranularity(Frame& frame, TextGranularity granularity)
2115c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
2128abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    VisibleSelection selection = frame.selection().selection();
2135c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    selection.expandUsingGranularity(granularity);
2145c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    RefPtr<Range> newRange = selection.toNormalizedRange();
2155c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    if (!newRange)
2165c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return false;
2171fad5ca6c42d689812b66fc493992aa6d747a6fbBen Murdoch    if (newRange->collapsed(IGNORE_EXCEPTION))
2185c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return false;
2198abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    RefPtr<Range> oldRange = frame.selection().selection().toNormalizedRange();
2208abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    EAffinity affinity = frame.selection().affinity();
2218abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().setSelectedRange(newRange.get(), affinity, true);
2225c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
2235c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
2245c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
225c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static TriState stateStyle(Frame& frame, CSSPropertyID propertyID, const char* desiredValue)
2265c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
227c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    if (frame.editor().behavior().shouldToggleStyleBasedOnStartOfSelection())
228c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)        return frame.editor().selectionStartHasStyle(propertyID, desiredValue) ? TrueTriState : FalseTriState;
229c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    return frame.editor().selectionHasStyle(propertyID, desiredValue);
2305c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
2315c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
232c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static String valueStyle(Frame& frame, CSSPropertyID propertyID)
2335c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
2345c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // FIXME: Rather than retrieving the style at the start of the current selection,
2355c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // we should retrieve the style present throughout the selection for non-Mac platforms.
236c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    return frame.editor().selectionStartCSSPropertyValue(propertyID);
2375c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
2385c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
239c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static TriState stateTextWritingDirection(Frame& frame, WritingDirection direction)
2405c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
2415c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    bool hasNestedOrMultipleEmbeddings;
2428abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    WritingDirection selectionDirection = EditingStyle::textDirectionForSelection(frame.selection().selection(),
2438abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)        frame.selection().typingStyle(), hasNestedOrMultipleEmbeddings);
2445c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // FXIME: We should be returning MixedTriState when selectionDirection == direction && hasNestedOrMultipleEmbeddings
2455c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return (selectionDirection == direction && !hasNestedOrMultipleEmbeddings) ? TrueTriState : FalseTriState;
2465c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
2475c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
248c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static unsigned verticalScrollDistance(Frame& frame)
2495c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
250c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    Element* focusedElement = frame.document()->focusedElement();
2517757ec2eadfa2dd8ac2aeed0a4399e9b07ec38cbBen Murdoch    if (!focusedElement)
2525c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return 0;
2537757ec2eadfa2dd8ac2aeed0a4399e9b07ec38cbBen Murdoch    RenderObject* renderer = focusedElement->renderer();
2545c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    if (!renderer || !renderer->isBox())
2555c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return 0;
2565c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    RenderStyle* style = renderer->style();
2575c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    if (!style)
2585c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return 0;
2597757ec2eadfa2dd8ac2aeed0a4399e9b07ec38cbBen Murdoch    if (!(style->overflowY() == OSCROLL || style->overflowY() == OAUTO || focusedElement->rendererIsEditable()))
2605c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return 0;
261c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    int height = std::min<int>(toRenderBox(renderer)->clientHeight(), frame.view()->visibleHeight());
262f5e4ad553afbc08dd2e729bb77e937a9a94d5827Torne (Richard Coles)    return static_cast<unsigned>(max(max<int>(height * ScrollableArea::minFractionToStepWhenPaging(), height - ScrollableArea::maxOverlapBetweenPages()), 1));
2635c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
2645c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
2655c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)static RefPtr<Range> unionDOMRanges(Range* a, Range* b)
2665c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
2671fad5ca6c42d689812b66fc493992aa6d747a6fbBen Murdoch    Range* start = a->compareBoundaryPoints(Range::START_TO_START, b, ASSERT_NO_EXCEPTION) <= 0 ? a : b;
2681fad5ca6c42d689812b66fc493992aa6d747a6fbBen Murdoch    Range* end = a->compareBoundaryPoints(Range::END_TO_END, b, ASSERT_NO_EXCEPTION) <= 0 ? b : a;
2695c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
270926b001d589ce2f10facb93dd4b87578ea35a855Torne (Richard Coles)    return Range::create(a->ownerDocument(), start->startContainer(), start->startOffset(), end->endContainer(), end->endOffset());
2715c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
2725c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
2735c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)// Execute command functions
2745c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
275c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeBackColor(Frame& frame, Event*, EditorCommandSource source, const String& value)
2765c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
2775c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return executeApplyStyle(frame, source, EditActionSetBackgroundColor, CSSPropertyBackgroundColor, value);
2785c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
2795c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
280c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeCopy(Frame& frame, Event*, EditorCommandSource, const String&)
2815c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
282c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    frame.editor().copy();
2835c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
2845c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
2855c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
286c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeCreateLink(Frame& frame, Event*, EditorCommandSource, const String& value)
2875c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
2885c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // FIXME: If userInterface is true, we should display a dialog box to let the user enter a URL.
2895c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    if (value.isEmpty())
2905c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return false;
2918abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    ASSERT(frame.document());
2928abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    CreateLinkCommand::create(*frame.document(), value)->apply();
2935c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
2945c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
2955c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
2961e202183a5dc46166763171984b285173f8585e5Torne (Richard Coles)static bool executeCut(Frame& frame, Event*, EditorCommandSource, const String&)
2975c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
2981e202183a5dc46166763171984b285173f8585e5Torne (Richard Coles)    frame.editor().cut();
2995c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
3005c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
3015c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
302c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeDefaultParagraphSeparator(Frame& frame, Event*, EditorCommandSource, const String& value)
3035c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
3045c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    if (equalIgnoringCase(value, "div"))
305c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)        frame.editor().setDefaultParagraphSeparator(EditorParagraphSeparatorIsDiv);
3065c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    else if (equalIgnoringCase(value, "p"))
307c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)        frame.editor().setDefaultParagraphSeparator(EditorParagraphSeparatorIsP);
3085c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
3095c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
3105c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
3115c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
312c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeDelete(Frame& frame, Event*, EditorCommandSource source, const String&)
3135c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
3145c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    switch (source) {
3155c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    case CommandFromMenuOrKeyBinding: {
3165c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        // Doesn't modify the text if the current selection isn't a range.
317c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)        frame.editor().performDelete();
3185c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return true;
3195c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    }
3205c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    case CommandFromDOM:
3215c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    case CommandFromDOMWithUserInterface:
3225c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        // If the current selection is a caret, delete the preceding character. IE performs forwardDelete, but we currently side with Firefox.
3235c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        // Doesn't scroll to make the selection visible, or modify the kill ring (this time, siding with IE, not Firefox).
3248abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)        ASSERT(frame.document());
3258abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)        TypingCommand::deleteKeyPressed(*frame.document(), frame.selection().granularity() == WordGranularity ? TypingCommand::SmartDelete : 0);
3265c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return true;
3275c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    }
3285c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    ASSERT_NOT_REACHED();
3295c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return false;
3305c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
3315c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
332c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeDeleteBackward(Frame& frame, Event*, EditorCommandSource, const String&)
3335c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
334c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    frame.editor().deleteWithDirection(DirectionBackward, CharacterGranularity, false, true);
3355c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
3365c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
3375c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
338c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeDeleteBackwardByDecomposingPreviousCharacter(Frame& frame, Event*, EditorCommandSource, const String&)
3395c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
340a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)    WTF_LOG_ERROR("DeleteBackwardByDecomposingPreviousCharacter is not implemented, doing DeleteBackward instead");
341c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    frame.editor().deleteWithDirection(DirectionBackward, CharacterGranularity, false, true);
3425c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
3435c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
3445c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
345c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeDeleteForward(Frame& frame, Event*, EditorCommandSource, const String&)
3465c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
347c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    frame.editor().deleteWithDirection(DirectionForward, CharacterGranularity, false, true);
3485c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
3495c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
3505c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
351c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeDeleteToBeginningOfLine(Frame& frame, Event*, EditorCommandSource, const String&)
3525c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
353c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    frame.editor().deleteWithDirection(DirectionBackward, LineBoundary, true, false);
3545c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
3555c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
3565c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
357c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeDeleteToBeginningOfParagraph(Frame& frame, Event*, EditorCommandSource, const String&)
3585c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
359c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    frame.editor().deleteWithDirection(DirectionBackward, ParagraphBoundary, true, false);
3605c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
3615c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
3625c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
363c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeDeleteToEndOfLine(Frame& frame, Event*, EditorCommandSource, const String&)
3645c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
3655c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // Despite its name, this command should delete the newline at the end of
3665c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // a paragraph if you are at the end of a paragraph (like DeleteToEndOfParagraph).
367c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    frame.editor().deleteWithDirection(DirectionForward, LineBoundary, true, false);
3685c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
3695c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
3705c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
371c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeDeleteToEndOfParagraph(Frame& frame, Event*, EditorCommandSource, const String&)
3725c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
3735c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // Despite its name, this command should delete the newline at the end of
3745c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // a paragraph if you are at the end of a paragraph.
375c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    frame.editor().deleteWithDirection(DirectionForward, ParagraphBoundary, true, false);
3765c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
3775c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
3785c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
379c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeDeleteToMark(Frame& frame, Event*, EditorCommandSource, const String&)
3805c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
381c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    RefPtr<Range> mark = frame.editor().mark().toNormalizedRange();
3825c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    if (mark) {
3838abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)        bool selected = frame.selection().setSelectedRange(unionDOMRanges(mark.get(), frame.editor().selectedRange().get()).get(), DOWNSTREAM, true);
3845c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        ASSERT(selected);
3855c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        if (!selected)
3865c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)            return false;
3875c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    }
388c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    frame.editor().performDelete();
3898abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.editor().setMark(frame.selection().selection());
3905c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
3915c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
3925c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
393c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeDeleteWordBackward(Frame& frame, Event*, EditorCommandSource, const String&)
3945c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
395c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    frame.editor().deleteWithDirection(DirectionBackward, WordGranularity, true, false);
3965c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
3975c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
3985c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
399c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeDeleteWordForward(Frame& frame, Event*, EditorCommandSource, const String&)
4005c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
401c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    frame.editor().deleteWithDirection(DirectionForward, WordGranularity, true, false);
4025c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
4035c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
4045c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
405c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeFindString(Frame& frame, Event*, EditorCommandSource, const String& value)
4065c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
407c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    return frame.editor().findString(value, true, false, true, false);
4085c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
4095c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
410c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeFontName(Frame& frame, Event*, EditorCommandSource source, const String& value)
4115c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
4125c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return executeApplyStyle(frame, source, EditActionSetFont, CSSPropertyFontFamily, value);
4135c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
4145c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
415c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeFontSize(Frame& frame, Event*, EditorCommandSource source, const String& value)
4165c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
4175267f701546148b83dfbe1d151cb184385bb5c22Torne (Richard Coles)    CSSValueID size;
4185c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    if (!HTMLFontElement::cssValueFromFontSizeNumber(value, size))
4195c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return false;
4205c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return executeApplyStyle(frame, source, EditActionChangeAttributes, CSSPropertyFontSize, size);
4215c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
4225c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
423c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeFontSizeDelta(Frame& frame, Event*, EditorCommandSource source, const String& value)
4245c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
4255c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return executeApplyStyle(frame, source, EditActionChangeAttributes, CSSPropertyWebkitFontSizeDelta, value);
4265c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
4275c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
428c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeForeColor(Frame& frame, Event*, EditorCommandSource source, const String& value)
4295c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
4305c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return executeApplyStyle(frame, source, EditActionSetColor, CSSPropertyColor, value);
4315c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
4325c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
433c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeFormatBlock(Frame& frame, Event*, EditorCommandSource, const String& value)
4345c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
4355c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    String tagName = value.lower();
4365c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    if (tagName[0] == '<' && tagName[tagName.length() - 1] == '>')
4375c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        tagName = tagName.substring(1, tagName.length() - 2);
4385c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
439a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)    AtomicString localName, prefix;
440a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)    if (!Document::parseQualifiedName(AtomicString(tagName), prefix, localName, IGNORE_EXCEPTION))
4415c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return false;
4425c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    QualifiedName qualifiedTagName(prefix, localName, xhtmlNamespaceURI);
4435c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
4448abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    ASSERT(frame.document());
4458abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    RefPtr<FormatBlockCommand> command = FormatBlockCommand::create(*frame.document(), qualifiedTagName);
4468abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    command->apply();
4475c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return command->didApply();
4485c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
4495c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
450c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeForwardDelete(Frame& frame, Event*, EditorCommandSource source, const String&)
4515c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
4525c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    switch (source) {
4535c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    case CommandFromMenuOrKeyBinding:
454c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)        frame.editor().deleteWithDirection(DirectionForward, CharacterGranularity, false, true);
4555c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return true;
4565c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    case CommandFromDOM:
4575c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    case CommandFromDOMWithUserInterface:
4585c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        // Doesn't scroll to make the selection visible, or modify the kill ring.
4595c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        // ForwardDelete is not implemented in IE or Firefox, so this behavior is only needed for
4605c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        // backward compatibility with ourselves, and for consistency with Delete.
4618abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)        ASSERT(frame.document());
4628abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)        TypingCommand::forwardDeleteKeyPressed(*frame.document());
4635c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return true;
4645c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    }
4655c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    ASSERT_NOT_REACHED();
4665c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return false;
4675c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
4685c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
469c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeIgnoreSpelling(Frame& frame, Event*, EditorCommandSource, const String&)
4705c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
4711e202183a5dc46166763171984b285173f8585e5Torne (Richard Coles)    frame.spellChecker().ignoreSpelling();
4725c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
4735c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
4745c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
475c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeIndent(Frame& frame, Event*, EditorCommandSource, const String&)
4765c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
4778abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    ASSERT(frame.document());
4788abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    IndentOutdentCommand::create(*frame.document(), IndentOutdentCommand::Indent)->apply();
4795c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
4805c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
4815c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
482c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeInsertBacktab(Frame& frame, Event* event, EditorCommandSource, const String&)
4835c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
484f79f16f17ddc4f842d7b7a38603e280e94be826aTorne (Richard Coles)    return targetFrame(frame, event)->eventHandler().handleTextInputEvent("\t", event, TextEventInputBackTab);
4855c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
4865c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
487c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeInsertHorizontalRule(Frame& frame, Event*, EditorCommandSource, const String& value)
4885c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
4898abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    ASSERT(frame.document());
4908abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    RefPtr<HTMLHRElement> rule = HTMLHRElement::create(*frame.document());
4915c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    if (!value.isEmpty())
492e08f70592b3fc0d5e68b9b914c9196e813720070Torne (Richard Coles)        rule->setIdAttribute(AtomicString(value));
4935c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return executeInsertNode(frame, rule.release());
4945c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
4955c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
496c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeInsertHTML(Frame& frame, Event*, EditorCommandSource, const String& value)
4975c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
4988abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    ASSERT(frame.document());
4998abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    return executeInsertFragment(frame, createFragmentFromMarkup(*frame.document(), value, ""));
5005c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
5015c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
502c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeInsertImage(Frame& frame, Event*, EditorCommandSource, const String& value)
5035c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
5045c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // FIXME: If userInterface is true, we should display a dialog box and let the user choose a local image.
5058abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    ASSERT(frame.document());
5068abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    RefPtr<HTMLImageElement> image = HTMLImageElement::create(*frame.document());
5075c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    image->setSrc(value);
5085c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return executeInsertNode(frame, image.release());
5095c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
5105c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
511c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeInsertLineBreak(Frame& frame, Event* event, EditorCommandSource source, const String&)
5125c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
5135c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    switch (source) {
5145c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    case CommandFromMenuOrKeyBinding:
515f79f16f17ddc4f842d7b7a38603e280e94be826aTorne (Richard Coles)        return targetFrame(frame, event)->eventHandler().handleTextInputEvent("\n", event, TextEventInputLineBreak);
5165c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    case CommandFromDOM:
5175c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    case CommandFromDOMWithUserInterface:
5185c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        // Doesn't scroll to make the selection visible, or modify the kill ring.
5195c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        // InsertLineBreak is not implemented in IE or Firefox, so this behavior is only needed for
5205c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        // backward compatibility with ourselves, and for consistency with other commands.
5218abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)        ASSERT(frame.document());
5228abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)        TypingCommand::insertLineBreak(*frame.document(), 0);
5235c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return true;
5245c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    }
5255c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    ASSERT_NOT_REACHED();
5265c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return false;
5275c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
5285c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
529c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeInsertNewline(Frame& frame, Event* event, EditorCommandSource, const String&)
5305c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
5315c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    Frame* targetFrame = WebCore::targetFrame(frame, event);
532f79f16f17ddc4f842d7b7a38603e280e94be826aTorne (Richard Coles)    return targetFrame->eventHandler().handleTextInputEvent("\n", event, targetFrame->editor().canEditRichly() ? TextEventInputKeyboard : TextEventInputLineBreak);
5335c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
5345c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
535c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeInsertNewlineInQuotedContent(Frame& frame, Event*, EditorCommandSource, const String&)
5365c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
5378abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    ASSERT(frame.document());
5388abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    TypingCommand::insertParagraphSeparatorInQuotedContent(*frame.document());
5395c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
5405c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
5415c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
542c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeInsertOrderedList(Frame& frame, Event*, EditorCommandSource, const String&)
5435c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
5448abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    ASSERT(frame.document());
5458abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    InsertListCommand::create(*frame.document(), InsertListCommand::OrderedList)->apply();
5465c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
5475c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
5485c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
549c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeInsertParagraph(Frame& frame, Event*, EditorCommandSource, const String&)
5505c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
5518abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    ASSERT(frame.document());
5528abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    TypingCommand::insertParagraphSeparator(*frame.document(), 0);
5535c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
5545c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
5555c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
556c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeInsertTab(Frame& frame, Event* event, EditorCommandSource, const String&)
5575c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
558f79f16f17ddc4f842d7b7a38603e280e94be826aTorne (Richard Coles)    return targetFrame(frame, event)->eventHandler().handleTextInputEvent("\t", event);
5595c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
5605c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
561c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeInsertText(Frame& frame, Event*, EditorCommandSource, const String& value)
5625c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
5638abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    ASSERT(frame.document());
5648abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    TypingCommand::insertText(*frame.document(), value, 0);
5655c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
5665c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
5675c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
568c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeInsertUnorderedList(Frame& frame, Event*, EditorCommandSource, const String&)
5695c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
5708abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    ASSERT(frame.document());
5718abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    InsertListCommand::create(*frame.document(), InsertListCommand::UnorderedList)->apply();
5725c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
5735c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
5745c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
575c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeJustifyCenter(Frame& frame, Event*, EditorCommandSource source, const String&)
5765c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
5775c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return executeApplyParagraphStyle(frame, source, EditActionCenter, CSSPropertyTextAlign, "center");
5785c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
5795c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
580c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeJustifyFull(Frame& frame, Event*, EditorCommandSource source, const String&)
5815c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
5825c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return executeApplyParagraphStyle(frame, source, EditActionJustify, CSSPropertyTextAlign, "justify");
5835c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
5845c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
585c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeJustifyLeft(Frame& frame, Event*, EditorCommandSource source, const String&)
5865c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
5875c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return executeApplyParagraphStyle(frame, source, EditActionAlignLeft, CSSPropertyTextAlign, "left");
5885c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
5895c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
590c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeJustifyRight(Frame& frame, Event*, EditorCommandSource source, const String&)
5915c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
5925c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return executeApplyParagraphStyle(frame, source, EditActionAlignRight, CSSPropertyTextAlign, "right");
5935c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
5945c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
595c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMakeTextWritingDirectionLeftToRight(Frame& frame, Event*, EditorCommandSource, const String&)
5965c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
59793ac45cfc74041c8ae536ce58a9534d46db2024eTorne (Richard Coles)    RefPtr<MutableStylePropertySet> style = MutableStylePropertySet::create();
5985c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    style->setProperty(CSSPropertyUnicodeBidi, CSSValueEmbed);
5995c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    style->setProperty(CSSPropertyDirection, CSSValueLtr);
600c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    frame.editor().applyStyle(style.get(), EditActionSetWritingDirection);
6015c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
6025c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
6035c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
604c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMakeTextWritingDirectionNatural(Frame& frame, Event*, EditorCommandSource, const String&)
6055c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
60693ac45cfc74041c8ae536ce58a9534d46db2024eTorne (Richard Coles)    RefPtr<MutableStylePropertySet> style = MutableStylePropertySet::create();
6075c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    style->setProperty(CSSPropertyUnicodeBidi, CSSValueNormal);
608c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    frame.editor().applyStyle(style.get(), EditActionSetWritingDirection);
6095c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
6105c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
6115c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
612c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMakeTextWritingDirectionRightToLeft(Frame& frame, Event*, EditorCommandSource, const String&)
6135c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
61493ac45cfc74041c8ae536ce58a9534d46db2024eTorne (Richard Coles)    RefPtr<MutableStylePropertySet> style = MutableStylePropertySet::create();
6155c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    style->setProperty(CSSPropertyUnicodeBidi, CSSValueEmbed);
6165c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    style->setProperty(CSSPropertyDirection, CSSValueRtl);
617c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    frame.editor().applyStyle(style.get(), EditActionSetWritingDirection);
6185c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
6195c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
6205c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
621c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveBackward(Frame& frame, Event*, EditorCommandSource, const String&)
6225c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
6238abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationMove, DirectionBackward, CharacterGranularity, UserTriggered);
6245c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
6255c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
6265c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
627c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveBackwardAndModifySelection(Frame& frame, Event*, EditorCommandSource, const String&)
6285c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
6298abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationExtend, DirectionBackward, CharacterGranularity, UserTriggered);
6305c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
6315c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
6325c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
633c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveDown(Frame& frame, Event*, EditorCommandSource, const String&)
6345c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
6358abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    return frame.selection().modify(FrameSelection::AlterationMove, DirectionForward, LineGranularity, UserTriggered);
6365c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
6375c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
638c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveDownAndModifySelection(Frame& frame, Event*, EditorCommandSource, const String&)
6395c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
6408abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationExtend, DirectionForward, LineGranularity, UserTriggered);
6415c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
6425c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
6435c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
644c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveForward(Frame& frame, Event*, EditorCommandSource, const String&)
6455c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
6468abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationMove, DirectionForward, CharacterGranularity, UserTriggered);
6475c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
6485c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
6495c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
650c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveForwardAndModifySelection(Frame& frame, Event*, EditorCommandSource, const String&)
6515c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
6528abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationExtend, DirectionForward, CharacterGranularity, UserTriggered);
6535c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
6545c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
6555c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
656c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveLeft(Frame& frame, Event*, EditorCommandSource, const String&)
6575c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
6588abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    return frame.selection().modify(FrameSelection::AlterationMove, DirectionLeft, CharacterGranularity, UserTriggered);
6595c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
6605c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
661c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveLeftAndModifySelection(Frame& frame, Event*, EditorCommandSource, const String&)
6625c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
6638abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationExtend, DirectionLeft, CharacterGranularity, UserTriggered);
6645c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
6655c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
6665c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
667c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMovePageDown(Frame& frame, Event*, EditorCommandSource, const String&)
6685c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
6695c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    unsigned distance = verticalScrollDistance(frame);
6705c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    if (!distance)
6715c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return false;
6728abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    return frame.selection().modify(FrameSelection::AlterationMove, distance, FrameSelection::DirectionDown,
6735c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        UserTriggered, FrameSelection::AlignCursorOnScrollAlways);
6745c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
6755c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
676c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMovePageDownAndModifySelection(Frame& frame, Event*, EditorCommandSource, const String&)
6775c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
6785c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    unsigned distance = verticalScrollDistance(frame);
6795c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    if (!distance)
6805c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return false;
6818abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    return frame.selection().modify(FrameSelection::AlterationExtend, distance, FrameSelection::DirectionDown,
6825c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        UserTriggered, FrameSelection::AlignCursorOnScrollAlways);
6835c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
6845c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
685c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMovePageUp(Frame& frame, Event*, EditorCommandSource, const String&)
6865c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
6875c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    unsigned distance = verticalScrollDistance(frame);
6885c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    if (!distance)
6895c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return false;
6908abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    return frame.selection().modify(FrameSelection::AlterationMove, distance, FrameSelection::DirectionUp,
6915c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        UserTriggered, FrameSelection::AlignCursorOnScrollAlways);
6925c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
6935c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
694c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMovePageUpAndModifySelection(Frame& frame, Event*, EditorCommandSource, const String&)
6955c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
6965c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    unsigned distance = verticalScrollDistance(frame);
6975c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    if (!distance)
6985c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return false;
6998abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    return frame.selection().modify(FrameSelection::AlterationExtend, distance, FrameSelection::DirectionUp,
7005c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        UserTriggered, FrameSelection::AlignCursorOnScrollAlways);
7015c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
7025c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
703c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveRight(Frame& frame, Event*, EditorCommandSource, const String&)
7045c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
7058abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    return frame.selection().modify(FrameSelection::AlterationMove, DirectionRight, CharacterGranularity, UserTriggered);
7065c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
7075c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
708c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveRightAndModifySelection(Frame& frame, Event*, EditorCommandSource, const String&)
7095c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
7108abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationExtend, DirectionRight, CharacterGranularity, UserTriggered);
7115c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
7125c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
7135c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
714c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveToBeginningOfDocument(Frame& frame, Event*, EditorCommandSource, const String&)
7155c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
7168abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationMove, DirectionBackward, DocumentBoundary, UserTriggered);
7175c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
7185c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
7195c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
720c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveToBeginningOfDocumentAndModifySelection(Frame& frame, Event*, EditorCommandSource, const String&)
7215c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
7228abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationExtend, DirectionBackward, DocumentBoundary, UserTriggered);
7235c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
7245c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
7255c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
726c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveToBeginningOfLine(Frame& frame, Event*, EditorCommandSource, const String&)
7275c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
7288abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationMove, DirectionBackward, LineBoundary, UserTriggered);
7295c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
7305c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
7315c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
732c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveToBeginningOfLineAndModifySelection(Frame& frame, Event*, EditorCommandSource, const String&)
7335c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
7348abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationExtend, DirectionBackward, LineBoundary, UserTriggered);
7355c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
7365c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
7375c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
738c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveToBeginningOfParagraph(Frame& frame, Event*, EditorCommandSource, const String&)
7395c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
7408abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationMove, DirectionBackward, ParagraphBoundary, UserTriggered);
7415c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
7425c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
7435c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
744c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveToBeginningOfParagraphAndModifySelection(Frame& frame, Event*, EditorCommandSource, const String&)
7455c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
7468abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationExtend, DirectionBackward, ParagraphBoundary, UserTriggered);
7475c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
7485c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
7495c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
750c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveToBeginningOfSentence(Frame& frame, Event*, EditorCommandSource, const String&)
7515c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
7528abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationMove, DirectionBackward, SentenceBoundary, UserTriggered);
7535c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
7545c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
7555c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
756c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveToBeginningOfSentenceAndModifySelection(Frame& frame, Event*, EditorCommandSource, const String&)
7575c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
7588abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationExtend, DirectionBackward, SentenceBoundary, UserTriggered);
7595c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
7605c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
7615c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
762c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveToEndOfDocument(Frame& frame, Event*, EditorCommandSource, const String&)
7635c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
7648abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationMove, DirectionForward, DocumentBoundary, UserTriggered);
7655c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
7665c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
7675c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
768c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveToEndOfDocumentAndModifySelection(Frame& frame, Event*, EditorCommandSource, const String&)
7695c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
7708abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationExtend, DirectionForward, DocumentBoundary, UserTriggered);
7715c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
7725c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
7735c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
774c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveToEndOfSentence(Frame& frame, Event*, EditorCommandSource, const String&)
7755c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
7768abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationMove, DirectionForward, SentenceBoundary, UserTriggered);
7775c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
7785c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
7795c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
780c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveToEndOfSentenceAndModifySelection(Frame& frame, Event*, EditorCommandSource, const String&)
7815c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
7828abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationExtend, DirectionForward, SentenceBoundary, UserTriggered);
7835c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
7845c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
7855c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
786c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveToEndOfLine(Frame& frame, Event*, EditorCommandSource, const String&)
7875c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
7888abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationMove, DirectionForward, LineBoundary, UserTriggered);
7895c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
7905c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
7915c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
792c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveToEndOfLineAndModifySelection(Frame& frame, Event*, EditorCommandSource, const String&)
7935c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
7948abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationExtend, DirectionForward, LineBoundary, UserTriggered);
7955c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
7965c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
7975c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
798c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveToEndOfParagraph(Frame& frame, Event*, EditorCommandSource, const String&)
7995c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
8008abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationMove, DirectionForward, ParagraphBoundary, UserTriggered);
8015c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
8025c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
8035c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
804c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveToEndOfParagraphAndModifySelection(Frame& frame, Event*, EditorCommandSource, const String&)
8055c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
8068abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationExtend, DirectionForward, ParagraphBoundary, UserTriggered);
8075c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
8085c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
8095c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
810c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveParagraphBackward(Frame& frame, Event*, EditorCommandSource, const String&)
811591b958dee2cf159d33a0b931e6231072eaf38d5Ben Murdoch{
8128abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationMove, DirectionBackward, ParagraphGranularity, UserTriggered);
813591b958dee2cf159d33a0b931e6231072eaf38d5Ben Murdoch    return true;
814591b958dee2cf159d33a0b931e6231072eaf38d5Ben Murdoch}
815591b958dee2cf159d33a0b931e6231072eaf38d5Ben Murdoch
816c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveParagraphBackwardAndModifySelection(Frame& frame, Event*, EditorCommandSource, const String&)
8175c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
8188abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationExtend, DirectionBackward, ParagraphGranularity, UserTriggered);
8195c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
8205c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
8215c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
822c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveParagraphForward(Frame& frame, Event*, EditorCommandSource, const String&)
823591b958dee2cf159d33a0b931e6231072eaf38d5Ben Murdoch{
8248abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationMove, DirectionForward, ParagraphGranularity, UserTriggered);
825591b958dee2cf159d33a0b931e6231072eaf38d5Ben Murdoch    return true;
826591b958dee2cf159d33a0b931e6231072eaf38d5Ben Murdoch}
827591b958dee2cf159d33a0b931e6231072eaf38d5Ben Murdoch
828c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveParagraphForwardAndModifySelection(Frame& frame, Event*, EditorCommandSource, const String&)
8295c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
8308abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationExtend, DirectionForward, ParagraphGranularity, UserTriggered);
8315c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
8325c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
8335c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
834c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveUp(Frame& frame, Event*, EditorCommandSource, const String&)
8355c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
8368abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    return frame.selection().modify(FrameSelection::AlterationMove, DirectionBackward, LineGranularity, UserTriggered);
8375c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
8385c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
839c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveUpAndModifySelection(Frame& frame, Event*, EditorCommandSource, const String&)
8405c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
8418abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationExtend, DirectionBackward, LineGranularity, UserTriggered);
8425c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
8435c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
8445c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
845c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveWordBackward(Frame& frame, Event*, EditorCommandSource, const String&)
8465c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
8478abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationMove, DirectionBackward, WordGranularity, UserTriggered);
8485c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
8495c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
8505c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
851c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveWordBackwardAndModifySelection(Frame& frame, Event*, EditorCommandSource, const String&)
8525c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
8538abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationExtend, DirectionBackward, WordGranularity, UserTriggered);
8545c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
8555c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
8565c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
857c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveWordForward(Frame& frame, Event*, EditorCommandSource, const String&)
8585c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
8598abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationMove, DirectionForward, WordGranularity, UserTriggered);
8605c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
8615c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
8625c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
863c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveWordForwardAndModifySelection(Frame& frame, Event*, EditorCommandSource, const String&)
8645c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
8658abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationExtend, DirectionForward, WordGranularity, UserTriggered);
8665c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
8675c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
8685c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
869c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveWordLeft(Frame& frame, Event*, EditorCommandSource, const String&)
8705c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
8718abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationMove, DirectionLeft, WordGranularity, UserTriggered);
8725c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
8735c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
8745c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
875c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveWordLeftAndModifySelection(Frame& frame, Event*, EditorCommandSource, const String&)
8765c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
8778abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationExtend, DirectionLeft, WordGranularity, UserTriggered);
8785c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
8795c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
8805c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
881c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveWordRight(Frame& frame, Event*, EditorCommandSource, const String&)
8825c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
8838abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationMove, DirectionRight, WordGranularity, UserTriggered);
8845c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
8855c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
8865c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
887c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveWordRightAndModifySelection(Frame& frame, Event*, EditorCommandSource, const String&)
8885c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
8898abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationExtend, DirectionRight, WordGranularity, UserTriggered);
8905c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
8915c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
8925c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
893c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveToLeftEndOfLine(Frame& frame, Event*, EditorCommandSource, const String&)
8945c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
8958abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationMove, DirectionLeft, LineBoundary, UserTriggered);
8965c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
8975c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
8985c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
899c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveToLeftEndOfLineAndModifySelection(Frame& frame, Event*, EditorCommandSource, const String&)
9005c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
9018abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationExtend, DirectionLeft, LineBoundary, UserTriggered);
9025c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
9035c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
9045c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
905c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveToRightEndOfLine(Frame& frame, Event*, EditorCommandSource, const String&)
9065c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
9078abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationMove, DirectionRight, LineBoundary, UserTriggered);
9085c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
9095c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
9105c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
911c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeMoveToRightEndOfLineAndModifySelection(Frame& frame, Event*, EditorCommandSource, const String&)
9125c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
9138abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().modify(FrameSelection::AlterationExtend, DirectionRight, LineBoundary, UserTriggered);
9145c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
9155c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
9165c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
917c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeOutdent(Frame& frame, Event*, EditorCommandSource, const String&)
9185c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
9198abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    ASSERT(frame.document());
9208abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    IndentOutdentCommand::create(*frame.document(), IndentOutdentCommand::Outdent)->apply();
9215c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
9225c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
9235c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
924c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeToggleOverwrite(Frame& frame, Event*, EditorCommandSource, const String&)
92553e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles){
926c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    frame.editor().toggleOverwriteModeEnabled();
92753e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)    return true;
92853e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)}
92953e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)
9301e202183a5dc46166763171984b285173f8585e5Torne (Richard Coles)static bool executePaste(Frame& frame, Event*, EditorCommandSource, const String&)
9315c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
9321e202183a5dc46166763171984b285173f8585e5Torne (Richard Coles)    frame.editor().paste();
9335c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
9345c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
9355c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
936c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executePasteGlobalSelection(Frame& frame, Event*, EditorCommandSource source, const String&)
9375c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
93851b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    if (!frame.editor().behavior().supportsGlobalSelection())
9395c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return false;
9405c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    ASSERT_UNUSED(source, source == CommandFromMenuOrKeyBinding);
9415c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
9425c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    bool oldSelectionMode = Pasteboard::generalPasteboard()->isSelectionMode();
9435c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    Pasteboard::generalPasteboard()->setSelectionMode(true);
944c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    frame.editor().paste();
9455c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    Pasteboard::generalPasteboard()->setSelectionMode(oldSelectionMode);
9465c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
9475c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
9485c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
9491e202183a5dc46166763171984b285173f8585e5Torne (Richard Coles)static bool executePasteAndMatchStyle(Frame& frame, Event*, EditorCommandSource, const String&)
9505c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
9511e202183a5dc46166763171984b285173f8585e5Torne (Richard Coles)    frame.editor().pasteAsPlainText();
9525c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
9535c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
9545c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
955c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executePrint(Frame& frame, Event*, EditorCommandSource, const String&)
9565c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
957c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    Page* page = frame.page();
9585c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    if (!page)
9595c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return false;
960c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    page->chrome().print(&frame);
9615c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
9625c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
9635c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
964c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeRedo(Frame& frame, Event*, EditorCommandSource, const String&)
9655c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
966c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    frame.editor().redo();
9675c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
9685c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
9695c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
970c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeRemoveFormat(Frame& frame, Event*, EditorCommandSource, const String&)
9715c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
972c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    frame.editor().removeFormattingAndStyle();
9735c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
9745c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
9755c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
976c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeScrollPageBackward(Frame& frame, Event*, EditorCommandSource, const String&)
9775c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
978e08f70592b3fc0d5e68b9b914c9196e813720070Torne (Richard Coles)    return frame.eventHandler().scrollRecursively(ScrollBlockDirectionBackward, ScrollByPage);
9795c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
9805c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
981c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeScrollPageForward(Frame& frame, Event*, EditorCommandSource, const String&)
9825c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
983e08f70592b3fc0d5e68b9b914c9196e813720070Torne (Richard Coles)    return frame.eventHandler().scrollRecursively(ScrollBlockDirectionForward, ScrollByPage);
9845c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
9855c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
986c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeScrollLineUp(Frame& frame, Event*, EditorCommandSource, const String&)
9875c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
988f79f16f17ddc4f842d7b7a38603e280e94be826aTorne (Richard Coles)    return frame.eventHandler().scrollRecursively(ScrollUp, ScrollByLine);
9895c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
9905c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
991c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeScrollLineDown(Frame& frame, Event*, EditorCommandSource, const String&)
9925c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
993f79f16f17ddc4f842d7b7a38603e280e94be826aTorne (Richard Coles)    return frame.eventHandler().scrollRecursively(ScrollDown, ScrollByLine);
9945c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
9955c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
996c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeScrollToBeginningOfDocument(Frame& frame, Event*, EditorCommandSource, const String&)
9975c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
998e08f70592b3fc0d5e68b9b914c9196e813720070Torne (Richard Coles)    return frame.eventHandler().scrollRecursively(ScrollBlockDirectionBackward, ScrollByDocument);
9995c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
10005c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1001c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeScrollToEndOfDocument(Frame& frame, Event*, EditorCommandSource, const String&)
10025c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
1003e08f70592b3fc0d5e68b9b914c9196e813720070Torne (Richard Coles)    return frame.eventHandler().scrollRecursively(ScrollBlockDirectionForward, ScrollByDocument);
10045c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
10055c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1006c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeSelectAll(Frame& frame, Event*, EditorCommandSource, const String&)
10075c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
10088abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().selectAll();
10095c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
10105c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
10115c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1012c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeSelectLine(Frame& frame, Event*, EditorCommandSource, const String&)
10135c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
10145c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return expandSelectionToGranularity(frame, LineGranularity);
10155c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
10165c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1017c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeSelectParagraph(Frame& frame, Event*, EditorCommandSource, const String&)
10185c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
10195c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return expandSelectionToGranularity(frame, ParagraphGranularity);
10205c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
10215c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1022c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeSelectSentence(Frame& frame, Event*, EditorCommandSource, const String&)
10235c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
10245c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return expandSelectionToGranularity(frame, SentenceGranularity);
10255c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
10265c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1027c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeSelectToMark(Frame& frame, Event*, EditorCommandSource, const String&)
10285c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
1029c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    RefPtr<Range> mark = frame.editor().mark().toNormalizedRange();
1030c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    RefPtr<Range> selection = frame.editor().selectedRange();
10311e202183a5dc46166763171984b285173f8585e5Torne (Richard Coles)    if (!mark || !selection)
10325c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return false;
10338abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().setSelectedRange(unionDOMRanges(mark.get(), selection.get()).get(), DOWNSTREAM, true);
10345c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
10355c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
10365c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1037c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeSelectWord(Frame& frame, Event*, EditorCommandSource, const String&)
10385c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
10395c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return expandSelectionToGranularity(frame, WordGranularity);
10405c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
10415c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1042c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeSetMark(Frame& frame, Event*, EditorCommandSource, const String&)
10435c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
10448abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.editor().setMark(frame.selection().selection());
10455c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
10465c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
10475c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1048c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeStrikethrough(Frame& frame, Event*, EditorCommandSource source, const String&)
10495c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
10505c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    RefPtr<CSSPrimitiveValue> lineThrough = CSSPrimitiveValue::createIdentifier(CSSValueLineThrough);
10515c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return executeToggleStyleInList(frame, source, EditActionUnderline, CSSPropertyWebkitTextDecorationsInEffect, lineThrough.get());
10525c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
10535c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1054c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeStyleWithCSS(Frame& frame, Event*, EditorCommandSource, const String& value)
10555c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
1056c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    frame.editor().setShouldStyleWithCSS(!equalIgnoringCase(value, "false"));
10575c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
10585c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
10595c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1060c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeUseCSS(Frame& frame, Event*, EditorCommandSource, const String& value)
10615c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
1062c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    frame.editor().setShouldStyleWithCSS(equalIgnoringCase(value, "false"));
10635c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
10645c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
10655c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1066c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeSubscript(Frame& frame, Event*, EditorCommandSource source, const String&)
10675c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
10685c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return executeToggleStyle(frame, source, EditActionSubscript, CSSPropertyVerticalAlign, "baseline", "sub");
10695c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
10705c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1071c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeSuperscript(Frame& frame, Event*, EditorCommandSource source, const String&)
10725c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
10735c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return executeToggleStyle(frame, source, EditActionSuperscript, CSSPropertyVerticalAlign, "baseline", "super");
10745c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
10755c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1076c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeSwapWithMark(Frame& frame, Event*, EditorCommandSource, const String&)
10775c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
1078c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    const VisibleSelection& mark = frame.editor().mark();
10798abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    const VisibleSelection& selection = frame.selection().selection();
10801e202183a5dc46166763171984b285173f8585e5Torne (Richard Coles)    if (mark.isNone() || selection.isNone())
10815c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return false;
10828abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().setSelection(mark);
1083c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    frame.editor().setMark(selection);
10845c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
10855c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
10865c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1087c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeToggleBold(Frame& frame, Event*, EditorCommandSource source, const String&)
10885c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
1089926b001d589ce2f10facb93dd4b87578ea35a855Torne (Richard Coles)    return executeToggleStyle(frame, source, EditActionBold, CSSPropertyFontWeight, "normal", "bold");
10905c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
10915c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1092c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeToggleItalic(Frame& frame, Event*, EditorCommandSource source, const String&)
10935c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
1094926b001d589ce2f10facb93dd4b87578ea35a855Torne (Richard Coles)    return executeToggleStyle(frame, source, EditActionItalics, CSSPropertyFontStyle, "normal", "italic");
10955c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
10965c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1097c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeTranspose(Frame& frame, Event*, EditorCommandSource, const String&)
10985c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
1099c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    frame.editor().transpose();
11005c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
11015c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
11025c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1103c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeUnderline(Frame& frame, Event*, EditorCommandSource source, const String&)
11045c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
11055c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    RefPtr<CSSPrimitiveValue> underline = CSSPrimitiveValue::createIdentifier(CSSValueUnderline);
11065c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return executeToggleStyleInList(frame, source, EditActionUnderline, CSSPropertyWebkitTextDecorationsInEffect, underline.get());
11075c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
11085c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1109c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeUndo(Frame& frame, Event*, EditorCommandSource, const String&)
11105c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
1111c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    frame.editor().undo();
11125c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
11135c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
11145c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1115c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeUnlink(Frame& frame, Event*, EditorCommandSource, const String&)
11165c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
11178abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    ASSERT(frame.document());
11188abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    UnlinkCommand::create(*frame.document())->apply();
11195c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
11205c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
11215c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1122c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeUnscript(Frame& frame, Event*, EditorCommandSource source, const String&)
11235c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
11245c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return executeApplyStyle(frame, source, EditActionUnscript, CSSPropertyVerticalAlign, "baseline");
11255c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
11265c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1127c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeUnselect(Frame& frame, Event*, EditorCommandSource, const String&)
11285c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
11298abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    frame.selection().clear();
11305c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
11315c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
11325c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1133c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeYank(Frame& frame, Event*, EditorCommandSource, const String&)
11345c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
113551b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    frame.editor().insertTextWithoutSendingTextEvent(frame.editor().killRing().yank(), false, 0);
113651b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    frame.editor().killRing().setToYankedState();
11375c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
11385c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
11395c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1140c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool executeYankAndSelect(Frame& frame, Event*, EditorCommandSource, const String&)
11415c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
114251b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    frame.editor().insertTextWithoutSendingTextEvent(frame.editor().killRing().yank(), true, 0);
114351b2906e11752df6c18351cf520e30522d3b53a1Torne (Richard Coles)    frame.editor().killRing().setToYankedState();
11445c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
11455c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
11465c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
11475c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)// Supported functions
11485c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
11495c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)static bool supported(Frame*)
11505c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
11515c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
11525c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
11535c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
11545c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)static bool supportedFromMenuOrKeyBinding(Frame*)
11555c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
11565c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return false;
11575c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
11585c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
11595c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)static bool supportedCopyCut(Frame* frame)
11605c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
11615c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    if (!frame)
11625c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return false;
11635c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
11645c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    Settings* settings = frame->settings();
11655c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    bool defaultValue = settings && settings->javaScriptCanAccessClipboard();
1166c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    return frame->editor().client().canCopyCut(frame, defaultValue);
11675c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
11685c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
11695c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)static bool supportedPaste(Frame* frame)
11705c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
11715c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    if (!frame)
11725c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return false;
11735c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
11745c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    Settings* settings = frame->settings();
1175926b001d589ce2f10facb93dd4b87578ea35a855Torne (Richard Coles)    bool defaultValue = settings && settings->javaScriptCanAccessClipboard() && settings->DOMPasteAllowed();
1176c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    return frame->editor().client().canPaste(frame, defaultValue);
11775c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
11785c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
11795c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)// Enabled functions
11805c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1181c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool enabled(Frame&, Event*, EditorCommandSource)
11825c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
11835c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return true;
11845c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
11855c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1186c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool enabledVisibleSelection(Frame& frame, Event* event, EditorCommandSource)
11875c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
11885c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // The term "visible" here includes a caret in editable text or a range in any text.
1189c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    const VisibleSelection& selection = frame.editor().selectionForCommand(event);
11905c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return (selection.isCaret() && selection.isContentEditable()) || selection.isRange();
11915c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
11925c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1193c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool caretBrowsingEnabled(Frame& frame)
11945c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
1195c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    return frame.settings() && frame.settings()->caretBrowsingEnabled();
11965c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
11975c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
11985c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)static EditorCommandSource dummyEditorCommandSource = static_cast<EditorCommandSource>(0);
11995c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1200c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool enabledVisibleSelectionOrCaretBrowsing(Frame& frame, Event* event, EditorCommandSource)
12015c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
12025c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // The EditorCommandSource parameter is unused in enabledVisibleSelection, so just pass a dummy variable
12035c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return caretBrowsingEnabled(frame) || enabledVisibleSelection(frame, event, dummyEditorCommandSource);
12045c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
12055c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1206c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool enabledVisibleSelectionAndMark(Frame& frame, Event* event, EditorCommandSource)
12075c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
1208c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    const VisibleSelection& selection = frame.editor().selectionForCommand(event);
12095c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return ((selection.isCaret() && selection.isContentEditable()) || selection.isRange())
1210c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)        && frame.editor().mark().isCaretOrRange();
12115c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
12125c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1213c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool enableCaretInEditableText(Frame& frame, Event* event, EditorCommandSource)
12145c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
1215c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    const VisibleSelection& selection = frame.editor().selectionForCommand(event);
12165c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return selection.isCaret() && selection.isContentEditable();
12175c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
12185c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1219c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool enabledCopy(Frame& frame, Event*, EditorCommandSource)
12205c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
1221c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    return frame.editor().canDHTMLCopy() || frame.editor().canCopy();
12225c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
12235c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1224c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool enabledCut(Frame& frame, Event*, EditorCommandSource)
12255c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
1226c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    return frame.editor().canDHTMLCut() || frame.editor().canCut();
12275c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
12285c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1229c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool enabledInEditableText(Frame& frame, Event* event, EditorCommandSource)
12305c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
1231c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    return frame.editor().selectionForCommand(event).rootEditableElement();
12325c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
12335c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1234c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool enabledDelete(Frame& frame, Event* event, EditorCommandSource source)
12355c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
12365c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    switch (source) {
123702772c6a72f1ee0b226341a4f4439970c29fc861Ben Murdoch    case CommandFromMenuOrKeyBinding:
1238c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)        return frame.editor().canDelete();
12395c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    case CommandFromDOM:
12405c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    case CommandFromDOMWithUserInterface:
12415c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        // "Delete" from DOM is like delete/backspace keypress, affects selected range if non-empty,
12425c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        // otherwise removes a character
12435c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return enabledInEditableText(frame, event, source);
12445c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    }
12455c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    ASSERT_NOT_REACHED();
12465c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return false;
12475c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
12485c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1249c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool enabledInEditableTextOrCaretBrowsing(Frame& frame, Event* event, EditorCommandSource)
12505c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
12515c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // The EditorCommandSource parameter is unused in enabledInEditableText, so just pass a dummy variable
12525c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return caretBrowsingEnabled(frame) || enabledInEditableText(frame, event, dummyEditorCommandSource);
12535c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
12545c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1255c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool enabledInRichlyEditableText(Frame& frame, Event*, EditorCommandSource)
12565c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
12578abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    return frame.selection().isCaretOrRange() && frame.selection().isContentRichlyEditable() && frame.selection().rootEditableElement();
12585c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
12595c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1260c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool enabledPaste(Frame& frame, Event*, EditorCommandSource)
12615c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
1262c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    return frame.editor().canPaste();
12635c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
12645c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1265c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool enabledRangeInEditableText(Frame& frame, Event*, EditorCommandSource)
12665c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
12678abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    return frame.selection().isRange() && frame.selection().isContentEditable();
12685c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
12695c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1270c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool enabledRangeInRichlyEditableText(Frame& frame, Event*, EditorCommandSource)
12715c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
12728abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    return frame.selection().isRange() && frame.selection().isContentRichlyEditable();
12735c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
12745c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1275c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool enabledRedo(Frame& frame, Event*, EditorCommandSource)
12765c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
1277c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    return frame.editor().canRedo();
12785c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
12795c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1280c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static bool enabledUndo(Frame& frame, Event*, EditorCommandSource)
12815c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
1282c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    return frame.editor().canUndo();
12835c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
12845c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
12855c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)// State functions
12865c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1287c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static TriState stateNone(Frame&, Event*)
12885c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
12895c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return FalseTriState;
12905c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
12915c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1292c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static TriState stateBold(Frame& frame, Event*)
12935c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
12945c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return stateStyle(frame, CSSPropertyFontWeight, "bold");
12955c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
12965c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1297c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static TriState stateItalic(Frame& frame, Event*)
12985c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
12995c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return stateStyle(frame, CSSPropertyFontStyle, "italic");
13005c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
13015c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1302c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static TriState stateOrderedList(Frame& frame, Event*)
13035c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
1304c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    return frame.editor().selectionOrderedListState();
13055c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
13065c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1307c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static TriState stateStrikethrough(Frame& frame, Event*)
13085c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
13095c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return stateStyle(frame, CSSPropertyWebkitTextDecorationsInEffect, "line-through");
13105c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
13115c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1312c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static TriState stateStyleWithCSS(Frame& frame, Event*)
13135c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
1314c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    return frame.editor().shouldStyleWithCSS() ? TrueTriState : FalseTriState;
13155c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
13165c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1317c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static TriState stateSubscript(Frame& frame, Event*)
13185c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
13195c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return stateStyle(frame, CSSPropertyVerticalAlign, "sub");
13205c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
13215c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1322c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static TriState stateSuperscript(Frame& frame, Event*)
13235c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
13245c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return stateStyle(frame, CSSPropertyVerticalAlign, "super");
13255c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
13265c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1327c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static TriState stateTextWritingDirectionLeftToRight(Frame& frame, Event*)
13285c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
13295c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return stateTextWritingDirection(frame, LeftToRightWritingDirection);
13305c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
13315c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1332c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static TriState stateTextWritingDirectionNatural(Frame& frame, Event*)
13335c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
13345c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return stateTextWritingDirection(frame, NaturalWritingDirection);
13355c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
13365c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1337c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static TriState stateTextWritingDirectionRightToLeft(Frame& frame, Event*)
13385c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
13395c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return stateTextWritingDirection(frame, RightToLeftWritingDirection);
13405c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
13415c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1342c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static TriState stateUnderline(Frame& frame, Event*)
13435c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
13445c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return stateStyle(frame, CSSPropertyWebkitTextDecorationsInEffect, "underline");
13455c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
13465c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1347c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static TriState stateUnorderedList(Frame& frame, Event*)
13485c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
1349c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    return frame.editor().selectionUnorderedListState();
13505c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
13515c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1352c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static TriState stateJustifyCenter(Frame& frame, Event*)
13535c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
13545c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return stateStyle(frame, CSSPropertyTextAlign, "center");
13555c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
13565c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1357c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static TriState stateJustifyFull(Frame& frame, Event*)
13585c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
13595c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return stateStyle(frame, CSSPropertyTextAlign, "justify");
13605c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
13615c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1362c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static TriState stateJustifyLeft(Frame& frame, Event*)
13635c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
13645c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return stateStyle(frame, CSSPropertyTextAlign, "left");
13655c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
13665c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1367c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static TriState stateJustifyRight(Frame& frame, Event*)
13685c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
13695c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return stateStyle(frame, CSSPropertyTextAlign, "right");
13705c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
13715c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
13725c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)// Value functions
13735c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1374c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static String valueNull(Frame&, Event*)
13755c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
13765c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return String();
13775c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
13785c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1379c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static String valueBackColor(Frame& frame, Event*)
13805c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
13815c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return valueStyle(frame, CSSPropertyBackgroundColor);
13825c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
13835c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1384c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static String valueDefaultParagraphSeparator(Frame& frame, Event*)
13855c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
1386c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    switch (frame.editor().defaultParagraphSeparator()) {
13875c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    case EditorParagraphSeparatorIsDiv:
13885c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return divTag.localName();
13895c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    case EditorParagraphSeparatorIsP:
13905c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return pTag.localName();
13915c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    }
13925c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
13935c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    ASSERT_NOT_REACHED();
13945c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return String();
13955c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
13965c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1397c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static String valueFontName(Frame& frame, Event*)
13985c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
13995c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return valueStyle(frame, CSSPropertyFontFamily);
14005c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
14015c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1402c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static String valueFontSize(Frame& frame, Event*)
14035c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
14045c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return valueStyle(frame, CSSPropertyFontSize);
14055c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
14065c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1407c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static String valueFontSizeDelta(Frame& frame, Event*)
14085c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
14095c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return valueStyle(frame, CSSPropertyWebkitFontSizeDelta);
14105c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
14115c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1412c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static String valueForeColor(Frame& frame, Event*)
14135c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
14145c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return valueStyle(frame, CSSPropertyColor);
14155c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
14165c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
1417c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)static String valueFormatBlock(Frame& frame, Event*)
14185c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
14198abfc5808a4e34d6e03867af8bc440dee641886fTorne (Richard Coles)    const VisibleSelection& selection = frame.selection().selection();
14205c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    if (!selection.isNonOrphanedCaretOrRange() || !selection.isContentEditable())
14215c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return "";
14225c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    Element* formatBlockElement = FormatBlockCommand::elementForFormatBlockCommand(selection.firstRange().get());
14235c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    if (!formatBlockElement)
14245c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return "";
14255c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return formatBlockElement->localName();
14265c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
14275c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
14285c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)// Map of functions
14295c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
14305c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)struct CommandEntry {
14315c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    const char* name;
14325c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    EditorInternalCommand command;
14335c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)};
14345c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
14355c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)static const CommandMap& createCommandMap()
14365c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
14375c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    static const CommandEntry commands[] = {
14385c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "AlignCenter", { executeJustifyCenter, supportedFromMenuOrKeyBinding, enabledInRichlyEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14395c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "AlignJustified", { executeJustifyFull, supportedFromMenuOrKeyBinding, enabledInRichlyEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14405c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "AlignLeft", { executeJustifyLeft, supportedFromMenuOrKeyBinding, enabledInRichlyEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14415c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "AlignRight", { executeJustifyRight, supportedFromMenuOrKeyBinding, enabledInRichlyEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14425c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "BackColor", { executeBackColor, supported, enabledInRichlyEditableText, stateNone, valueBackColor, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14435c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "BackwardDelete", { executeDeleteBackward, supportedFromMenuOrKeyBinding, enabledInEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } }, // FIXME: remove BackwardDelete when Safari for Windows stops using it.
14445c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "Bold", { executeToggleBold, supported, enabledInRichlyEditableText, stateBold, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14455c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "Copy", { executeCopy, supportedCopyCut, enabledCopy, stateNone, valueNull, notTextInsertion, allowExecutionWhenDisabled } },
14465c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "CreateLink", { executeCreateLink, supported, enabledInRichlyEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14475c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "Cut", { executeCut, supportedCopyCut, enabledCut, stateNone, valueNull, notTextInsertion, allowExecutionWhenDisabled } },
14485c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "DefaultParagraphSeparator", { executeDefaultParagraphSeparator, supported, enabled, stateNone, valueDefaultParagraphSeparator, notTextInsertion, doNotAllowExecutionWhenDisabled} },
14495c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "Delete", { executeDelete, supported, enabledDelete, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14505c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "DeleteBackward", { executeDeleteBackward, supportedFromMenuOrKeyBinding, enabledInEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14515c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "DeleteBackwardByDecomposingPreviousCharacter", { executeDeleteBackwardByDecomposingPreviousCharacter, supportedFromMenuOrKeyBinding, enabledInEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14525c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "DeleteForward", { executeDeleteForward, supportedFromMenuOrKeyBinding, enabledInEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14535c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "DeleteToBeginningOfLine", { executeDeleteToBeginningOfLine, supportedFromMenuOrKeyBinding, enabledInEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14545c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "DeleteToBeginningOfParagraph", { executeDeleteToBeginningOfParagraph, supportedFromMenuOrKeyBinding, enabledInEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14555c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "DeleteToEndOfLine", { executeDeleteToEndOfLine, supportedFromMenuOrKeyBinding, enabledInEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14565c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "DeleteToEndOfParagraph", { executeDeleteToEndOfParagraph, supportedFromMenuOrKeyBinding, enabledInEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14575c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "DeleteToMark", { executeDeleteToMark, supportedFromMenuOrKeyBinding, enabledInEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14585c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "DeleteWordBackward", { executeDeleteWordBackward, supportedFromMenuOrKeyBinding, enabledInEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14595c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "DeleteWordForward", { executeDeleteWordForward, supportedFromMenuOrKeyBinding, enabledInEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14605c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "FindString", { executeFindString, supported, enabled, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14615c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "FontName", { executeFontName, supported, enabledInEditableText, stateNone, valueFontName, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14625c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "FontSize", { executeFontSize, supported, enabledInEditableText, stateNone, valueFontSize, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14635c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "FontSizeDelta", { executeFontSizeDelta, supported, enabledInEditableText, stateNone, valueFontSizeDelta, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14645c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "ForeColor", { executeForeColor, supported, enabledInRichlyEditableText, stateNone, valueForeColor, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14655c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "FormatBlock", { executeFormatBlock, supported, enabledInRichlyEditableText, stateNone, valueFormatBlock, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14665c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "ForwardDelete", { executeForwardDelete, supported, enabledInEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14675c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "HiliteColor", { executeBackColor, supported, enabledInRichlyEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14685c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "IgnoreSpelling", { executeIgnoreSpelling, supportedFromMenuOrKeyBinding, enabledInEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14695c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "Indent", { executeIndent, supported, enabledInRichlyEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14705c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "InsertBacktab", { executeInsertBacktab, supportedFromMenuOrKeyBinding, enabledInEditableText, stateNone, valueNull, isTextInsertion, doNotAllowExecutionWhenDisabled } },
14715c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "InsertHTML", { executeInsertHTML, supported, enabledInEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14725c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "InsertHorizontalRule", { executeInsertHorizontalRule, supported, enabledInRichlyEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14735c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "InsertImage", { executeInsertImage, supported, enabledInRichlyEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14745c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "InsertLineBreak", { executeInsertLineBreak, supported, enabledInEditableText, stateNone, valueNull, isTextInsertion, doNotAllowExecutionWhenDisabled } },
147502772c6a72f1ee0b226341a4f4439970c29fc861Ben Murdoch        { "InsertNewline", { executeInsertNewline, supportedFromMenuOrKeyBinding, enabledInEditableText, stateNone, valueNull, isTextInsertion, doNotAllowExecutionWhenDisabled } },
14765c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "InsertNewlineInQuotedContent", { executeInsertNewlineInQuotedContent, supported, enabledInRichlyEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14775c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "InsertOrderedList", { executeInsertOrderedList, supported, enabledInRichlyEditableText, stateOrderedList, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14785c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "InsertParagraph", { executeInsertParagraph, supported, enabledInEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14795c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "InsertTab", { executeInsertTab, supportedFromMenuOrKeyBinding, enabledInEditableText, stateNone, valueNull, isTextInsertion, doNotAllowExecutionWhenDisabled } },
14805c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "InsertText", { executeInsertText, supported, enabledInEditableText, stateNone, valueNull, isTextInsertion, doNotAllowExecutionWhenDisabled } },
14815c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "InsertUnorderedList", { executeInsertUnorderedList, supported, enabledInRichlyEditableText, stateUnorderedList, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14825c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "Italic", { executeToggleItalic, supported, enabledInRichlyEditableText, stateItalic, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14835c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "JustifyCenter", { executeJustifyCenter, supported, enabledInRichlyEditableText, stateJustifyCenter, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14845c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "JustifyFull", { executeJustifyFull, supported, enabledInRichlyEditableText, stateJustifyFull, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14855c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "JustifyLeft", { executeJustifyLeft, supported, enabledInRichlyEditableText, stateJustifyLeft, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14865c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "JustifyNone", { executeJustifyLeft, supported, enabledInRichlyEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14875c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "JustifyRight", { executeJustifyRight, supported, enabledInRichlyEditableText, stateJustifyRight, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14885c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MakeTextWritingDirectionLeftToRight", { executeMakeTextWritingDirectionLeftToRight, supportedFromMenuOrKeyBinding, enabledInRichlyEditableText, stateTextWritingDirectionLeftToRight, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14895c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MakeTextWritingDirectionNatural", { executeMakeTextWritingDirectionNatural, supportedFromMenuOrKeyBinding, enabledInRichlyEditableText, stateTextWritingDirectionNatural, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14905c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MakeTextWritingDirectionRightToLeft", { executeMakeTextWritingDirectionRightToLeft, supportedFromMenuOrKeyBinding, enabledInRichlyEditableText, stateTextWritingDirectionRightToLeft, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14915c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveBackward", { executeMoveBackward, supportedFromMenuOrKeyBinding, enabledInEditableTextOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14925c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveBackwardAndModifySelection", { executeMoveBackwardAndModifySelection, supportedFromMenuOrKeyBinding, enabledVisibleSelectionOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14935c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveDown", { executeMoveDown, supportedFromMenuOrKeyBinding, enabledInEditableTextOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14945c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveDownAndModifySelection", { executeMoveDownAndModifySelection, supportedFromMenuOrKeyBinding, enabledVisibleSelectionOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14955c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveForward", { executeMoveForward, supportedFromMenuOrKeyBinding, enabledInEditableTextOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14965c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveForwardAndModifySelection", { executeMoveForwardAndModifySelection, supportedFromMenuOrKeyBinding, enabledVisibleSelectionOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14975c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveLeft", { executeMoveLeft, supportedFromMenuOrKeyBinding, enabledInEditableTextOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14985c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveLeftAndModifySelection", { executeMoveLeftAndModifySelection, supportedFromMenuOrKeyBinding, enabledVisibleSelectionOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
14995c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MovePageDown", { executeMovePageDown, supportedFromMenuOrKeyBinding, enabledInEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15005c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MovePageDownAndModifySelection", { executeMovePageDownAndModifySelection, supportedFromMenuOrKeyBinding, enabledVisibleSelection, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15015c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MovePageUp", { executeMovePageUp, supportedFromMenuOrKeyBinding, enabledInEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15025c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MovePageUpAndModifySelection", { executeMovePageUpAndModifySelection, supportedFromMenuOrKeyBinding, enabledVisibleSelection, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
1503591b958dee2cf159d33a0b931e6231072eaf38d5Ben Murdoch        { "MoveParagraphBackward", { executeMoveParagraphBackward, supportedFromMenuOrKeyBinding, enabledInEditableTextOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15045c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveParagraphBackwardAndModifySelection", { executeMoveParagraphBackwardAndModifySelection, supportedFromMenuOrKeyBinding, enabledVisibleSelectionOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
1505591b958dee2cf159d33a0b931e6231072eaf38d5Ben Murdoch        { "MoveParagraphForward", { executeMoveParagraphForward, supportedFromMenuOrKeyBinding, enabledInEditableTextOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15065c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveParagraphForwardAndModifySelection", { executeMoveParagraphForwardAndModifySelection, supportedFromMenuOrKeyBinding, enabledVisibleSelectionOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15075c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveRight", { executeMoveRight, supportedFromMenuOrKeyBinding, enabledInEditableTextOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15085c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveRightAndModifySelection", { executeMoveRightAndModifySelection, supportedFromMenuOrKeyBinding, enabledVisibleSelectionOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15095c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveToBeginningOfDocument", { executeMoveToBeginningOfDocument, supportedFromMenuOrKeyBinding, enabledInEditableTextOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15105c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveToBeginningOfDocumentAndModifySelection", { executeMoveToBeginningOfDocumentAndModifySelection, supportedFromMenuOrKeyBinding, enabledVisibleSelectionOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15115c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveToBeginningOfLine", { executeMoveToBeginningOfLine, supportedFromMenuOrKeyBinding, enabledInEditableTextOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15125c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveToBeginningOfLineAndModifySelection", { executeMoveToBeginningOfLineAndModifySelection, supportedFromMenuOrKeyBinding, enabledVisibleSelectionOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15135c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveToBeginningOfParagraph", { executeMoveToBeginningOfParagraph, supportedFromMenuOrKeyBinding, enabledInEditableTextOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15145c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveToBeginningOfParagraphAndModifySelection", { executeMoveToBeginningOfParagraphAndModifySelection, supportedFromMenuOrKeyBinding, enabledVisibleSelectionOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15155c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveToBeginningOfSentence", { executeMoveToBeginningOfSentence, supportedFromMenuOrKeyBinding, enabledInEditableTextOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15165c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveToBeginningOfSentenceAndModifySelection", { executeMoveToBeginningOfSentenceAndModifySelection, supportedFromMenuOrKeyBinding, enabledVisibleSelectionOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15175c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveToEndOfDocument", { executeMoveToEndOfDocument, supportedFromMenuOrKeyBinding, enabledInEditableTextOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15185c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveToEndOfDocumentAndModifySelection", { executeMoveToEndOfDocumentAndModifySelection, supportedFromMenuOrKeyBinding, enabledVisibleSelectionOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15195c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveToEndOfLine", { executeMoveToEndOfLine, supportedFromMenuOrKeyBinding, enabledInEditableTextOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15205c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveToEndOfLineAndModifySelection", { executeMoveToEndOfLineAndModifySelection, supportedFromMenuOrKeyBinding, enabledVisibleSelectionOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15215c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveToEndOfParagraph", { executeMoveToEndOfParagraph, supportedFromMenuOrKeyBinding, enabledInEditableTextOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15225c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveToEndOfParagraphAndModifySelection", { executeMoveToEndOfParagraphAndModifySelection, supportedFromMenuOrKeyBinding, enabledVisibleSelectionOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15235c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveToEndOfSentence", { executeMoveToEndOfSentence, supportedFromMenuOrKeyBinding, enabledInEditableTextOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15245c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveToEndOfSentenceAndModifySelection", { executeMoveToEndOfSentenceAndModifySelection, supportedFromMenuOrKeyBinding, enabledVisibleSelectionOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15255c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveToLeftEndOfLine", { executeMoveToLeftEndOfLine, supportedFromMenuOrKeyBinding, enabledInEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15265c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveToLeftEndOfLineAndModifySelection", { executeMoveToLeftEndOfLineAndModifySelection, supportedFromMenuOrKeyBinding, enabledInEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15275c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveToRightEndOfLine", { executeMoveToRightEndOfLine, supportedFromMenuOrKeyBinding, enabledInEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15285c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveToRightEndOfLineAndModifySelection", { executeMoveToRightEndOfLineAndModifySelection, supportedFromMenuOrKeyBinding, enabledInEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15295c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveUp", { executeMoveUp, supportedFromMenuOrKeyBinding, enabledInEditableTextOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15305c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveUpAndModifySelection", { executeMoveUpAndModifySelection, supportedFromMenuOrKeyBinding, enabledVisibleSelectionOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15315c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveWordBackward", { executeMoveWordBackward, supportedFromMenuOrKeyBinding, enabledInEditableTextOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15325c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveWordBackwardAndModifySelection", { executeMoveWordBackwardAndModifySelection, supportedFromMenuOrKeyBinding, enabledVisibleSelectionOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15335c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveWordForward", { executeMoveWordForward, supportedFromMenuOrKeyBinding, enabledInEditableTextOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15345c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveWordForwardAndModifySelection", { executeMoveWordForwardAndModifySelection, supportedFromMenuOrKeyBinding, enabledVisibleSelectionOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15355c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveWordLeft", { executeMoveWordLeft, supportedFromMenuOrKeyBinding, enabledInEditableTextOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15365c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveWordLeftAndModifySelection", { executeMoveWordLeftAndModifySelection, supportedFromMenuOrKeyBinding, enabledVisibleSelectionOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15375c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveWordRight", { executeMoveWordRight, supportedFromMenuOrKeyBinding, enabledInEditableTextOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15385c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "MoveWordRightAndModifySelection", { executeMoveWordRightAndModifySelection, supportedFromMenuOrKeyBinding, enabledVisibleSelectionOrCaretBrowsing, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15395c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "Outdent", { executeOutdent, supported, enabledInRichlyEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
154053e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)        { "OverWrite", { executeToggleOverwrite, supportedFromMenuOrKeyBinding, enabledInRichlyEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15415c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "Paste", { executePaste, supportedPaste, enabledPaste, stateNone, valueNull, notTextInsertion, allowExecutionWhenDisabled } },
15425c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "PasteAndMatchStyle", { executePasteAndMatchStyle, supportedPaste, enabledPaste, stateNone, valueNull, notTextInsertion, allowExecutionWhenDisabled } },
15435c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "PasteGlobalSelection", { executePasteGlobalSelection, supportedFromMenuOrKeyBinding, enabledPaste, stateNone, valueNull, notTextInsertion, allowExecutionWhenDisabled } },
15445c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "Print", { executePrint, supported, enabled, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15455c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "Redo", { executeRedo, supported, enabledRedo, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15465c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "RemoveFormat", { executeRemoveFormat, supported, enabledRangeInEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15475c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "ScrollPageBackward", { executeScrollPageBackward, supportedFromMenuOrKeyBinding, enabled, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15485c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "ScrollPageForward", { executeScrollPageForward, supportedFromMenuOrKeyBinding, enabled, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15495c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "ScrollLineUp", { executeScrollLineUp, supportedFromMenuOrKeyBinding, enabled, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15505c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "ScrollLineDown", { executeScrollLineDown, supportedFromMenuOrKeyBinding, enabled, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15515c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "ScrollToBeginningOfDocument", { executeScrollToBeginningOfDocument, supportedFromMenuOrKeyBinding, enabled, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15525c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "ScrollToEndOfDocument", { executeScrollToEndOfDocument, supportedFromMenuOrKeyBinding, enabled, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15535c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "SelectAll", { executeSelectAll, supported, enabled, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15545c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "SelectLine", { executeSelectLine, supportedFromMenuOrKeyBinding, enabledVisibleSelection, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15555c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "SelectParagraph", { executeSelectParagraph, supportedFromMenuOrKeyBinding, enabledVisibleSelection, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15565c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "SelectSentence", { executeSelectSentence, supportedFromMenuOrKeyBinding, enabledVisibleSelection, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15575c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "SelectToMark", { executeSelectToMark, supportedFromMenuOrKeyBinding, enabledVisibleSelectionAndMark, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15585c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "SelectWord", { executeSelectWord, supportedFromMenuOrKeyBinding, enabledVisibleSelection, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15595c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "SetMark", { executeSetMark, supportedFromMenuOrKeyBinding, enabledVisibleSelection, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15605c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "Strikethrough", { executeStrikethrough, supported, enabledInRichlyEditableText, stateStrikethrough, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15615c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "StyleWithCSS", { executeStyleWithCSS, supported, enabled, stateStyleWithCSS, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15625c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "Subscript", { executeSubscript, supported, enabledInRichlyEditableText, stateSubscript, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15635c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "Superscript", { executeSuperscript, supported, enabledInRichlyEditableText, stateSuperscript, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15645c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "SwapWithMark", { executeSwapWithMark, supportedFromMenuOrKeyBinding, enabledVisibleSelectionAndMark, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15655c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "ToggleBold", { executeToggleBold, supportedFromMenuOrKeyBinding, enabledInRichlyEditableText, stateBold, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15665c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "ToggleItalic", { executeToggleItalic, supportedFromMenuOrKeyBinding, enabledInRichlyEditableText, stateItalic, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15675c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "ToggleUnderline", { executeUnderline, supportedFromMenuOrKeyBinding, enabledInRichlyEditableText, stateUnderline, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15685c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "Transpose", { executeTranspose, supported, enableCaretInEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15695c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "Underline", { executeUnderline, supported, enabledInRichlyEditableText, stateUnderline, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15705c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "Undo", { executeUndo, supported, enabledUndo, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15715c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "Unlink", { executeUnlink, supported, enabledRangeInRichlyEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15725c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "Unscript", { executeUnscript, supportedFromMenuOrKeyBinding, enabledInRichlyEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15735c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "Unselect", { executeUnselect, supported, enabledVisibleSelection, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15745c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "UseCSS", { executeUseCSS, supported, enabled, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15755c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "Yank", { executeYank, supportedFromMenuOrKeyBinding, enabledInEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15765c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        { "YankAndSelect", { executeYankAndSelect, supportedFromMenuOrKeyBinding, enabledInEditableText, stateNone, valueNull, notTextInsertion, doNotAllowExecutionWhenDisabled } },
15775c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    };
15785c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
15795c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // These unsupported commands are listed here since they appear in the Microsoft
15805c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // documentation used as the starting point for our DOM executeCommand support.
15815c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    //
15825c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // 2D-Position (not supported)
15835c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // AbsolutePosition (not supported)
15845c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // BlockDirLTR (not supported)
15855c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // BlockDirRTL (not supported)
15865c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // BrowseMode (not supported)
15875c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // ClearAuthenticationCache (not supported)
15885c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // CreateBookmark (not supported)
15895c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // DirLTR (not supported)
15905c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // DirRTL (not supported)
15915c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // EditMode (not supported)
15925c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // InlineDirLTR (not supported)
15935c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // InlineDirRTL (not supported)
15945c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // InsertButton (not supported)
15955c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // InsertFieldSet (not supported)
15965c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // InsertIFrame (not supported)
15975c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // InsertInputButton (not supported)
15985c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // InsertInputCheckbox (not supported)
15995c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // InsertInputFileUpload (not supported)
16005c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // InsertInputHidden (not supported)
16015c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // InsertInputImage (not supported)
16025c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // InsertInputPassword (not supported)
16035c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // InsertInputRadio (not supported)
16045c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // InsertInputReset (not supported)
16055c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // InsertInputSubmit (not supported)
16065c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // InsertInputText (not supported)
16075c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // InsertMarquee (not supported)
16085c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // InsertSelectDropDown (not supported)
16095c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // InsertSelectListBox (not supported)
16105c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // InsertTextArea (not supported)
16115c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // LiveResize (not supported)
16125c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // MultipleSelection (not supported)
16135c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // Open (not supported)
16145c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // PlayImage (not supported)
16155c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // Refresh (not supported)
16165c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // RemoveParaFormat (not supported)
16175c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // SaveAs (not supported)
16185c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // SizeToControl (not supported)
16195c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // SizeToControlHeight (not supported)
16205c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // SizeToControlWidth (not supported)
16215c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // Stop (not supported)
16225c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // StopImage (not supported)
16235c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // Unbookmark (not supported)
16245c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
16255c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    CommandMap& commandMap = *new CommandMap;
16265c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
16275c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    for (size_t i = 0; i < WTF_ARRAY_LENGTH(commands); ++i) {
16285c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        ASSERT(!commandMap.get(commands[i].name));
16295c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        commandMap.set(commands[i].name, &commands[i].command);
16305c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    }
16315c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
16325c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return commandMap;
16335c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
16345c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
16355c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)static const EditorInternalCommand* internalCommand(const String& commandName)
16365c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
16375c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    static const CommandMap& commandMap = createCommandMap();
16385c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return commandName.isEmpty() ? 0 : commandMap.get(commandName);
16395c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
16405c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
16415c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)Editor::Command Editor::command(const String& commandName)
16425c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
16431e202183a5dc46166763171984b285173f8585e5Torne (Richard Coles)    return Command(internalCommand(commandName), CommandFromMenuOrKeyBinding, &m_frame);
16445c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
16455c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
16465c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)Editor::Command Editor::command(const String& commandName, EditorCommandSource source)
16475c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
16481e202183a5dc46166763171984b285173f8585e5Torne (Richard Coles)    return Command(internalCommand(commandName), source, &m_frame);
16495c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
16505c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
16515c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)bool Editor::commandIsSupportedFromMenuOrKeyBinding(const String& commandName)
16525c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
16535c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return internalCommand(commandName);
16545c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
16555c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
16565c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)Editor::Command::Command()
16575c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    : m_command(0)
16585c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
16595c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
16605c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
16615c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)Editor::Command::Command(const EditorInternalCommand* command, EditorCommandSource source, PassRefPtr<Frame> frame)
16625c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    : m_command(command)
16635c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    , m_source(source)
16645c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    , m_frame(command ? frame : 0)
16655c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
16665c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    // Use separate assertions so we can tell which bad thing happened.
16675c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    if (!command)
16685c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        ASSERT(!m_frame);
16695c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    else
16705c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        ASSERT(m_frame);
16715c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
16725c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
16735c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)bool Editor::Command::execute(const String& parameter, Event* triggeringEvent) const
16745c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
16755c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    if (!isEnabled(triggeringEvent)) {
16765c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        // Let certain commands be executed when performed explicitly even if they are disabled.
16775c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        if (!isSupported() || !m_frame || !m_command->allowExecutionWhenDisabled)
16785c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)            return false;
16795c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    }
16805c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    m_frame->document()->updateLayoutIgnorePendingStylesheets();
1681c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    return m_command->execute(*m_frame, triggeringEvent, m_source, parameter);
16825c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
16835c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
16845c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)bool Editor::Command::execute(Event* triggeringEvent) const
16855c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
16865c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return execute(String(), triggeringEvent);
16875c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
16885c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
16895c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)bool Editor::Command::isSupported() const
16905c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
16915c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    if (!m_command)
16925c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return false;
16935c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    switch (m_source) {
16945c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    case CommandFromMenuOrKeyBinding:
16955c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return true;
16965c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    case CommandFromDOM:
16975c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    case CommandFromDOMWithUserInterface:
16985c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return m_command->isSupportedFromDOM(m_frame.get());
16995c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    }
17005c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    ASSERT_NOT_REACHED();
17015c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return false;
17025c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
17035c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
17045c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)bool Editor::Command::isEnabled(Event* triggeringEvent) const
17055c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
17065c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    if (!isSupported() || !m_frame)
17075c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return false;
1708c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    return m_command->isEnabled(*m_frame, triggeringEvent, m_source);
17095c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
17105c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
17115c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)TriState Editor::Command::state(Event* triggeringEvent) const
17125c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
17135c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    if (!isSupported() || !m_frame)
17145c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return FalseTriState;
1715c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    return m_command->state(*m_frame, triggeringEvent);
17165c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
17175c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
17185c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)String Editor::Command::value(Event* triggeringEvent) const
17195c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
17205c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    if (!isSupported() || !m_frame)
17215c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)        return String();
17225c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    if (m_command->value == valueNull && m_command->state != stateNone)
1723c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)        return m_command->state(*m_frame, triggeringEvent) == TrueTriState ? "true" : "false";
1724c0e19a689c8ac22cdc96b291a8d33a5d3b0b34a4Torne (Richard Coles)    return m_command->value(*m_frame, triggeringEvent);
17255c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
17265c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
17275c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)bool Editor::Command::isTextInsertion() const
17285c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles){
17295c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)    return m_command && m_command->isTextInsertion;
17305c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)}
17315c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)
17325c87bf8b86a7c82ef50fb7a89697d8e02e2553beTorne (Richard Coles)} // namespace WebCore
1733