Reviewed by Trey.
authormjs <mjs@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Sat, 22 May 2004 01:50:48 +0000 (01:50 +0000)
committermjs <mjs@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Sat, 22 May 2004 01:50:48 +0000 (01:50 +0000)
<rdar://problem/3656722>: Implement outerText and setOuterText DOM extensions

        * khtml/html/html_elementimpl.cpp:
        (HTMLElementImpl::outerText): Return same value as innerText().
        (HTMLElementImpl::setInnerText): Fix comment.
        (HTMLElementImpl::setOuterText): Replace node with text, merge neighboring text nodes.
        * khtml/html/html_elementimpl.h: Prototype new methods.
* khtml/dom/html_element.cpp:
        (HTMLElement::outerText): Hook up to impl.
        (HTMLElement::setOuterText): Ditto.
        * khtml/dom/html_element.h: Prototype new methods.
        * khtml/ecma/kjs_html.cpp:
        (KJS::HTMLElement::getValueProperty): Glue up outerText.
        (KJS::HTMLElement::putValue): Ditto.
        * khtml/ecma/kjs_html.h: Added new enum value.
        * khtml/ecma/kjs_html.lut.h:
        (KJS::): Regenerated.

git-svn-id: https://svn.webkit.org/repository/webkit/trunk@6666 268f45cc-cd09-0410-ab3c-d52691b4dbfc

WebCore/ChangeLog-2005-08-23
WebCore/khtml/dom/html_element.cpp
WebCore/khtml/dom/html_element.h
WebCore/khtml/ecma/kjs_html.cpp
WebCore/khtml/ecma/kjs_html.h
WebCore/khtml/ecma/kjs_html.lut.h
WebCore/khtml/html/html_elementimpl.cpp
WebCore/khtml/html/html_elementimpl.h

index bffda26..8195022 100644 (file)
@@ -1,3 +1,25 @@
+2004-05-21  Maciej Stachowiak  <mjs@apple.com>
+
+        Reviewed by Trey.
+
+       <rdar://problem/3656722>: Implement outerText and setOuterText DOM extensions
+        
+        * khtml/html/html_elementimpl.cpp:
+        (HTMLElementImpl::outerText): Return same value as innerText().
+        (HTMLElementImpl::setInnerText): Fix comment.
+        (HTMLElementImpl::setOuterText): Replace node with text, merge neighboring text nodes.
+        * khtml/html/html_elementimpl.h: Prototype new methods.
+       * khtml/dom/html_element.cpp:
+        (HTMLElement::outerText): Hook up to impl.
+        (HTMLElement::setOuterText): Ditto.
+        * khtml/dom/html_element.h: Prototype new methods.
+        * khtml/ecma/kjs_html.cpp:
+        (KJS::HTMLElement::getValueProperty): Glue up outerText.
+        (KJS::HTMLElement::putValue): Ditto. 
+        * khtml/ecma/kjs_html.h: Added new enum value.
+        * khtml/ecma/kjs_html.lut.h:
+        (KJS::): Regenerated.
+
 2004-05-21  Richard Williamson   <rjw@apple.com>
 
         Removed _bindObject:forFrame: SPI.
index 0a45726..3546af1 100644 (file)
@@ -161,6 +161,21 @@ void HTMLElement::setOuterHTML( const DOMString &html )
        throw DOMException(DOMException::NO_MODIFICATION_ALLOWED_ERR);
 }
 
+DOMString HTMLElement::outerText() const
+{
+    if ( !impl ) return DOMString();
+    return ((HTMLElementImpl *)impl)->outerText();
+}
+
+void HTMLElement::setOuterText( const DOMString &text )
+{
+    bool ok = false;
+    if( impl )
+       ok = ((HTMLElementImpl *)impl)->setOuterText( text );
+    if ( !ok )
+       throw DOMException(DOMException::NO_MODIFICATION_ALLOWED_ERR);
+}
+
 HTMLCollection HTMLElement::children() const
 {
     if(!impl) return HTMLCollection();
index 8fc53dd..dff0247 100644 (file)
@@ -176,6 +176,15 @@ public:
     DOMString innerText() const;
 
     /**
+     * Set the text content of this node.
+     *
+     * @exception DOMException
+     * NO_MODIFICATION_ALLOWED_ERR: Raised if there is the element does not allow
+     * children.
+     */
+    void setInnerText( const DOMString &text );
+
+    /**
      * The HTML code of this element, including the element itself.
      * This function is not part of the DOM specifications as defined by the w3c.
      */
@@ -188,13 +197,19 @@ public:
     void setOuterHTML( const DOMString &html );
 
     /**
-     * Set the text content of this node.
+     * The text contained in this element.
+     * This function is not part of the DOM specifications as defined by the w3c.
+     */
+    DOMString outerText() const;
+
+    /**
+     * Replace this element with the given text
      *
      * @exception DOMException
      * NO_MODIFICATION_ALLOWED_ERR: Raised if there is the element does not allow
      * children.
      */
-    void setInnerText( const DOMString &text );
+    void setOuterText( const DOMString &text );
 
     /**
      * Retrieves a collection of nodes that are direct descendants of this node.
index 12fc40b..017f84a 100644 (file)
@@ -618,7 +618,7 @@ const ClassInfo* KJS::HTMLElement::classInfo() const
   }
 }
 /*
-@begin HTMLElementTable 13
+@begin HTMLElementTable 14
   id           KJS::HTMLElement::ElementId     DontDelete
   title                KJS::HTMLElement::ElementTitle  DontDelete
   lang         KJS::HTMLElement::ElementLang   DontDelete
@@ -628,6 +628,7 @@ const ClassInfo* KJS::HTMLElement::classInfo() const
   innerHTML    KJS::HTMLElement::ElementInnerHTML DontDelete
   innerText    KJS::HTMLElement::ElementInnerText DontDelete
   outerHTML    KJS::HTMLElement::ElementOuterHTML DontDelete
+  outerText    KJS::HTMLElement::ElementOuterText DontDelete
   document     KJS::HTMLElement::ElementDocument  DontDelete|ReadOnly
 # IE extension
   children     KJS::HTMLElement::ElementChildren  DontDelete|ReadOnly
@@ -1822,6 +1823,8 @@ Value KJS::HTMLElement::getValueProperty(ExecState *exec, int token) const
     return String(element.innerText());
   case ElementOuterHTML:
     return String(element.outerHTML());
+  case ElementOuterText:
+    return String(element.outerText());
   case ElementDocument:
     return getDOMNode(exec,element.ownerDocument());
   case ElementChildren:
@@ -2862,6 +2865,9 @@ void KJS::HTMLElement::putValue(ExecState *exec, int token, const Value& value,
   case ElementOuterHTML:
     element.setOuterHTML(str);
     return;
+  case ElementOuterText:
+    element.setOuterText(str);
+    return;
   case ElementContentEditable:
     element.setContentEditable(str);
     return;
index e1bfce8..17f4484 100644 (file)
@@ -148,7 +148,7 @@ namespace KJS {
            MarqueeStart, MarqueeStop,
            ElementInnerHTML, ElementTitle, ElementId, ElementDir, ElementLang,
            ElementClassName, ElementInnerText, ElementDocument, ElementChildren, ElementContentEditable,
-           ElementIsContentEditable, ElementOuterHTML};
+           ElementIsContentEditable, ElementOuterHTML, ElementOuterText};
 
     DOM::HTMLElement toElement() const { return static_cast<DOM::HTMLElement>(node); }
   };
index 6bac8e7..4e3660c 100644 (file)
@@ -51,25 +51,30 @@ const struct HashTable HTMLDocumentTable = { 2, 39, HTMLDocumentTableEntries, 30
 namespace KJS {
 
 const struct HashEntry HTMLElementTableEntries[] = {
-   { "title", KJS::HTMLElement::ElementTitle, DontDelete, 0, 0 },
+   { "title", KJS::HTMLElement::ElementTitle, DontDelete, 0, &HTMLElementTableEntries[17] },
+   { "children", KJS::HTMLElement::ElementChildren, DontDelete|ReadOnly, 0, 0 },
    { 0, 0, 0, 0, 0 },
-   { "lang", KJS::HTMLElement::ElementLang, DontDelete, 0, 0 },
-   { "isContentEditable", KJS::HTMLElement::ElementIsContentEditable, DontDelete|ReadOnly, 0, 0 },
-   { "innerHTML", KJS::HTMLElement::ElementInnerHTML, DontDelete, 0, 0 },
-   { "document", KJS::HTMLElement::ElementDocument, DontDelete|ReadOnly, 0, 0 },
+   { "contentEditable", KJS::HTMLElement::ElementContentEditable, DontDelete, 0, 0 },
    { 0, 0, 0, 0, 0 },
-   { "dir", KJS::HTMLElement::ElementDir, DontDelete, 0, 0 },
    { 0, 0, 0, 0, 0 },
-   { "className", KJS::HTMLElement::ElementClassName, DontDelete, 0, &HTMLElementTableEntries[14] },
-   { "id", KJS::HTMLElement::ElementId, DontDelete, 0, &HTMLElementTableEntries[13] },
    { 0, 0, 0, 0, 0 },
-   { "innerText", KJS::HTMLElement::ElementInnerText, DontDelete, 0, 0 },
-   { "outerHTML", KJS::HTMLElement::ElementOuterHTML, DontDelete, 0, &HTMLElementTableEntries[15] },
-   { "children", KJS::HTMLElement::ElementChildren, DontDelete|ReadOnly, 0, 0 },
-   { "contentEditable", KJS::HTMLElement::ElementContentEditable, DontDelete, 0, 0 }
+   { 0, 0, 0, 0, 0 },
+   { 0, 0, 0, 0, 0 },
+   { "id", KJS::HTMLElement::ElementId, DontDelete, 0, &HTMLElementTableEntries[14] },
+   { 0, 0, 0, 0, 0 },
+   { "dir", KJS::HTMLElement::ElementDir, DontDelete, 0, 0 },
+   { "lang", KJS::HTMLElement::ElementLang, DontDelete, 0, 0 },
+   { 0, 0, 0, 0, 0 },
+   { "className", KJS::HTMLElement::ElementClassName, DontDelete, 0, &HTMLElementTableEntries[15] },
+   { "innerHTML", KJS::HTMLElement::ElementInnerHTML, DontDelete, 0, &HTMLElementTableEntries[16] },
+   { "innerText", KJS::HTMLElement::ElementInnerText, DontDelete, 0, &HTMLElementTableEntries[19] },
+   { "outerHTML", KJS::HTMLElement::ElementOuterHTML, DontDelete, 0, &HTMLElementTableEntries[18] },
+   { "outerText", KJS::HTMLElement::ElementOuterText, DontDelete, 0, 0 },
+   { "document", KJS::HTMLElement::ElementDocument, DontDelete|ReadOnly, 0, &HTMLElementTableEntries[20] },
+   { "isContentEditable", KJS::HTMLElement::ElementIsContentEditable, DontDelete|ReadOnly, 0, 0 }
 };
 
-const struct HashTable HTMLElementTable = { 2, 16, HTMLElementTableEntries, 13 };
+const struct HashTable HTMLElementTable = { 2, 21, HTMLElementTableEntries, 14 };
 
 } // namespace
 
index efd023c..8fc0f71 100644 (file)
@@ -672,6 +672,14 @@ DOMString HTMLElementImpl::innerText() const
     return text;
 }
 
+DOMString HTMLElementImpl::outerText() const
+{
+    // getting outerText is the same as getting innerText, only
+    // setting is different.
+    return innerText();
+}
+
+
 DocumentFragmentImpl *HTMLElementImpl::createContextualFragment( const DOMString &html )
 {
     // the following is in accordance with the definition as used by IE
@@ -779,7 +787,7 @@ bool HTMLElementImpl::setInnerText( const DOMString &text )
     // following the IE specs.
     if( endTag[id()] == FORBIDDEN )
         return false;
-    // IE disallows innerHTML on inline elements. I don't see why we should have this restriction, as our
+    // IE disallows innerText on inline elements. I don't see why we should have this restriction, as our
     // dhtml engine can cope with it. Lars
     //if ( isInline() ) return false;
     switch( id() ) {
@@ -808,6 +816,67 @@ bool HTMLElementImpl::setInnerText( const DOMString &text )
     return false;
 }
 
+bool HTMLElementImpl::setOuterText( const DOMString &text )
+{
+    // following the IE specs.
+    if( endTag[id()] == FORBIDDEN )
+        return false;
+    switch( id() ) {
+        case ID_COL:
+        case ID_COLGROUP:
+        case ID_FRAMESET:
+        case ID_HEAD:
+        case ID_HTML:
+        case ID_TABLE:
+        case ID_TBODY:
+        case ID_TFOOT:
+        case ID_THEAD:
+        case ID_TR:
+            return false;
+        default:
+            break;
+    }
+
+    NodeBaseImpl *parent = static_cast<NodeBaseImpl *>(parentNode());
+
+    if (!parent) {
+       return false;
+    }
+
+    TextImpl *t = new TextImpl( docPtr(), text );
+    int ec = 0;
+    parent->replaceChild(t, this, ec);
+
+    if ( ec )
+        return false;
+
+    // is previous node a text node? if so, merge into it
+    NodeImpl *prev = t->previousSibling();
+    if (prev && prev->isTextNode()) {
+       TextImpl *textPrev = static_cast<TextImpl *>(prev);
+       textPrev->appendData(t->data(), ec);
+       t->parentNode()->removeChild(t, ec);
+       t = textPrev;
+    }
+
+    if ( ec )
+        return false;
+
+    // is next node a text node? if so, merge it in
+    NodeImpl *next = t->nextSibling();
+    if (next && next->isTextNode()) {
+       TextImpl *textNext = static_cast<TextImpl *>(next);
+       t->appendData(textNext->data(), ec);
+       textNext->parentNode()->removeChild(textNext, ec);
+    }
+
+    if ( ec )
+        return false;
+
+    return true;
+}
+
+
 DOMString HTMLElementImpl::namespaceURI() const
 {
     // For HTML documents, we treat HTML elements as having no namespace. But for XML documents
index bd5f8da..9642489 100644 (file)
@@ -148,10 +148,12 @@ public:
     DOMString innerHTML() const;
     DOMString outerHTML() const;
     DOMString innerText() const;
+    DOMString outerText() const;
     DocumentFragmentImpl *createContextualFragment( const DOMString &html );
     bool setInnerHTML( const DOMString &html );
     bool setOuterHTML( const DOMString &html );
     bool setInnerText( const DOMString &text );
+    bool setOuterText( const DOMString &text );
 
     virtual DOMString namespaceURI() const;