2010-12-01 Ilya Tikhonovsky <loislo@chromium.org>
[WebKit-https.git] / WebCore / inspector / front-end / DOMAgent.js
index 252b5f8..24e29ec 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2009 Google Inc. All rights reserved.
+ * Copyright (C) 2009, 2010 Google Inc. All rights reserved.
  * Copyright (C) 2009 Joseph Pecoraro
  *
  * Redistribution and use in source and binary forms, with or without
@@ -60,13 +60,28 @@ WebInspector.DOMNode = function(doc, payload) {
     this.style = null;
     this._matchedCSSRules = [];
 
-    if (this.nodeType == Node.ELEMENT_NODE) {
+    this.breakpoints = {};
+
+    if (this.nodeType === Node.ELEMENT_NODE) {
         // HTML and BODY from internal iframes should not overwrite top-level ones.
         if (!this.ownerDocument.documentElement && this.nodeName === "HTML")
             this.ownerDocument.documentElement = this;
         if (!this.ownerDocument.body && this.nodeName === "BODY")
             this.ownerDocument.body = this;
+        if (payload.documentURL)
+            this.documentURL = payload.documentURL;
+    } else if (this.nodeType === Node.DOCUMENT_TYPE_NODE) {
+        this.publicId = payload.publicId;
+        this.systemId = payload.systemId;
+        this.internalSubset = payload.internalSubset;
+    } else if (this.nodeType === Node.DOCUMENT_NODE) {
+        this.documentURL = payload.documentURL;
+    } else if (this.nodeType === Node.ATTRIBUTE_NODE) {
+        this.name = payload.name;
+        this.value = payload.value;
     }
+
+    InspectorBackend.registerDomainDispatcher("DOM", this);
 }
 
 WebInspector.DOMNode.prototype = {
@@ -75,7 +90,8 @@ WebInspector.DOMNode.prototype = {
         return this.attributes.length > 0;
     },
 
-    hasChildNodes: function()  {
+    hasChildNodes: function()
+    {
         return this._childNodeCount > 0;
     },
 
@@ -86,13 +102,7 @@ WebInspector.DOMNode.prototype = {
     set nodeValue(value) {
         if (this.nodeType != Node.TEXT_NODE)
             return;
-        var self = this;
-        var callback = function()
-        {
-            self._nodeValue = value;
-            self.textContent = value;
-        };
-        this.ownerDocument._domAgent.setTextNodeValueAsync(this, value, callback);
+        this.ownerDocument._domAgent.setTextNodeValueAsync(this, value, function() {});
     },
 
     getAttribute: function(name)
@@ -131,8 +141,22 @@ WebInspector.DOMNode.prototype = {
         this.ownerDocument._domAgent.removeAttributeAsync(this, name, callback);
     },
 
+    path: function()
+    {
+        var path = [];
+        var node = this;
+        while (node && "index" in node && node.nodeName.length) {
+            path.push([node.index, node.nodeName]);
+            node = node.parentNode;
+        }
+        path.reverse();
+        return path.join(",");
+    },
+
     _setAttributesPayload: function(attrs)
     {
+        this.attributes = [];
+        this._attributesMap = {};
         for (var i = 0; i < attrs.length; i += 2)
             this._addAttribute(attrs[i], attrs[i + 1]);
     },
@@ -140,10 +164,13 @@ WebInspector.DOMNode.prototype = {
     _insertChild: function(prev, payload)
     {
         var node = new WebInspector.DOMNode(this.ownerDocument, payload);
-        if (!prev)
-            // First node
-            this.children = [ node ];
-        else
+        if (!prev) {
+            if (!this.children) {
+                // First node
+                this.children = [ node ];
+            } else
+                this.children.unshift(node);
+        } else
             this.children.splice(this.children.indexOf(prev) + 1, 0, node);
         this._renumber();
         return node;
@@ -179,6 +206,7 @@ WebInspector.DOMNode.prototype = {
         this.lastChild = this.children[this._childNodeCount - 1];
         for (var i = 0; i < this._childNodeCount; ++i) {
             var child = this.children[i];
+            child.index = i;
             child.nextSibling = i + 1 < this._childNodeCount ? this.children[i + 1] : null;
             child.prevSibling = i - 1 >= 0 ? this.children[i - 1] : null;
             child.parentNode = this;
@@ -194,30 +222,6 @@ WebInspector.DOMNode.prototype = {
         };
         this._attributesMap[name] = attr;
         this.attributes.push(attr);
-    },
-
-    _setStyles: function(computedStyle, inlineStyle, styleAttributes, matchedCSSRules)
-    {
-        this._computedStyle = new WebInspector.CSSStyleDeclaration(computedStyle);
-        this.style = new WebInspector.CSSStyleDeclaration(inlineStyle);
-
-        for (var name in styleAttributes) {
-            if (this._attributesMap[name])
-                this._attributesMap[name].style = new WebInspector.CSSStyleDeclaration(styleAttributes[name]);
-        }
-
-        this._matchedCSSRules = [];
-        for (var i = 0; i < matchedCSSRules.length; i++)
-            this._matchedCSSRules.push(WebInspector.CSSStyleDeclaration.parseRule(matchedCSSRules[i]));
-    },
-
-    _clearStyles: function()
-    {
-        this.computedStyle = null;
-        this.style = null;
-        for (var name in this._attributesMap)
-            this._attributesMap[name].style = null;
-        this._matchedCSSRules = null;
     }
 }
 
@@ -291,16 +295,6 @@ WebInspector.DOMWindow.prototype = {
 
     Object: function()
     {
-    },
-
-    getComputedStyle: function(node)
-    {
-        return node._computedStyle;
-    },
-
-    getMatchedCSSRules: function(node, pseudoElement, authorOnly)
-    {
-        return node._matchedCSSRules;
     }
 }
 
@@ -326,26 +320,25 @@ WebInspector.DOMAgent.prototype = {
         function mycallback() {
             callback(parent.children);
         }
-        var callId = WebInspector.Callback.wrap(mycallback);
-        InspectorController.getChildNodes(callId, parent.id);
+        InspectorBackend.getChildNodes(parent.id, mycallback);
     },
 
     setAttributeAsync: function(node, name, value, callback)
     {
         var mycallback = this._didApplyDomChange.bind(this, node, callback);
-        InspectorController.setAttribute(WebInspector.Callback.wrap(mycallback), node.id, name, value);
+        InspectorBackend.setAttribute(node.id, name, value, mycallback);
     },
 
     removeAttributeAsync: function(node, name, callback)
     {
         var mycallback = this._didApplyDomChange.bind(this, node, callback);
-        InspectorController.removeAttribute(WebInspector.Callback.wrap(mycallback), node.id, name);
+        InspectorBackend.removeAttribute(node.id, name, mycallback);
     },
 
     setTextNodeValueAsync: function(node, text, callback)
     {
         var mycallback = this._didApplyDomChange.bind(this, node, callback);
-        InspectorController.setTextNodeValue(WebInspector.Callback.wrap(mycallback), node.id, text);
+        InspectorBackend.setTextNodeValue(node.id, text, mycallback);
     },
 
     _didApplyDomChange: function(node, callback, success)
@@ -355,31 +348,43 @@ WebInspector.DOMAgent.prototype = {
         callback();
         // TODO(pfeldman): Fix this hack.
         var elem = WebInspector.panels.elements.treeOutline.findTreeElement(node);
-        if (elem) {
-            elem._updateTitle();
-        }
+        if (elem)
+            elem.updateTitle();
     },
 
     _attributesUpdated: function(nodeId, attrsArray)
     {
         var node = this._idToDOMNode[nodeId];
         node._setAttributesPayload(attrsArray);
+        var event = {target: node};
+        this.document._fireDomEvent("DOMAttrModified", event);
+    },
+
+    _characterDataModified: function(nodeId, newValue)
+    {
+        var node = this._idToDOMNode[nodeId];
+        node._nodeValue = newValue;
+        node.textContent = newValue;
+        var event = { target : node };
+        this.document._fireDomEvent("DOMCharacterDataModified", event);
     },
 
-    nodeForId: function(nodeId) {
+    nodeForId: function(nodeId)
+    {
         return this._idToDOMNode[nodeId];
     },
 
     _setDocument: function(payload)
     {
         this._idToDOMNode = {};
-        if (payload) {
+        if (payload && "id" in payload) {
             this.document = new WebInspector.DOMDocument(this, this._window, payload);
             this._idToDOMNode[payload.id] = this.document;
             this._bindNodes(this.document.children);
+            WebInspector.breakpointManager.restoreDOMBreakpoints();
         } else
             this.document = null;
-        WebInspector.panels.elements.reset();
+        WebInspector.panels.elements.setDocument(this.document);
     },
 
     _setDetachedRoot: function(payload)
@@ -433,21 +438,47 @@ WebInspector.DOMAgent.prototype = {
         var event = { target : node, relatedNode : parent };
         this.document._fireDomEvent("DOMNodeRemoved", event);
         delete this._idToDOMNode[nodeId];
+        this._removeBreakpoints(node);
+    },
+
+    _removeBreakpoints: function(node)
+    {
+        for (var type in node.breakpoints)
+            node.breakpoints[type].remove();
+        if (!node.children)
+            return;
+        for (var i = 0; i < node.children.length; ++i)
+            this._removeBreakpoints(node.children[i]);
     }
 }
 
+WebInspector.ApplicationCache = {}
+
+WebInspector.ApplicationCache.getApplicationCachesAsync = function(callback)
+{
+    function mycallback(applicationCaches)
+    {
+        // FIXME: Currently, this list only returns a single application cache.
+        if (applicationCaches)
+            callback(applicationCaches);
+    }
+
+    InspectorBackend.getApplicationCaches(mycallback);
+}
+
 WebInspector.Cookies = {}
 
-WebInspector.Cookies.getCookiesAsync = function(callback, cookieDomain)
+WebInspector.Cookies.getCookiesAsync = function(callback)
 {
-    function mycallback(cookies, cookiesString) {
+    function mycallback(cookies, cookiesString)
+    {
         if (cookiesString)
             callback(WebInspector.Cookies.buildCookiesFromString(cookiesString), false);
         else
             callback(cookies, true);
     }
-    var callId = WebInspector.Callback.wrap(mycallback);
-    InspectorController.getCookies(callId, cookieDomain);
+
+    InspectorBackend.getCookies(mycallback);
 }
 
 WebInspector.Cookies.buildCookiesFromString = function(rawCookieString)
@@ -469,149 +500,30 @@ WebInspector.Cookies.buildCookiesFromString = function(rawCookieString)
     return cookies;
 }
 
-WebInspector.EventListeners = {}
-
-WebInspector.EventListeners.getEventListenersForNodeAsync = function(node, callback)
+WebInspector.Cookies.cookieMatchesResourceURL = function(cookie, resourceURL)
 {
-    if (!node)
-        return;
-
-    var callId = WebInspector.Callback.wrap(callback);
-    InspectorController.getEventListenersForNode(callId, node.id);
+    var url = resourceURL.asParsedURL();
+    if (!url || !this.cookieDomainMatchesResourceDomain(cookie.domain, url.host))
+        return false;
+    return (url.path.indexOf(cookie.path) === 0
+        && (!cookie.port || url.port == cookie.port)
+        && (!cookie.secure || url.scheme === "https"));
 }
 
-WebInspector.CSSStyleDeclaration = function(payload)
+WebInspector.Cookies.cookieDomainMatchesResourceDomain = function(cookieDomain, resourceDomain)
 {
-    this.id = payload.id;
-    this.width = payload.width;
-    this.height = payload.height;
-    this.__disabledProperties = payload.__disabledProperties;
-    this.__disabledPropertyValues = payload.__disabledPropertyValues;
-    this.__disabledPropertyPriorities = payload.__disabledPropertyPriorities;
-    this.uniqueStyleProperties = payload.uniqueStyleProperties;
-    this._shorthandValues = payload.shorthandValues;
-    this._propertyMap = {};
-    this._longhandProperties = {};
-    this.length = payload.properties.length;
-
-    for (var i = 0; i < this.length; ++i) {
-        var property = payload.properties[i];
-        var name = property.name;
-        this[i] = name;
-        this._propertyMap[name] = property;
-    }
-
-    // Index longhand properties.
-    for (var i = 0; i < this.uniqueStyleProperties.length; ++i) {
-        var name = this.uniqueStyleProperties[i];
-        var property = this._propertyMap[name];
-        if (property.shorthand) {
-            var longhands = this._longhandProperties[property.shorthand];
-            if (!longhands) {
-                longhands = [];
-                this._longhandProperties[property.shorthand] = longhands;
-            }
-            longhands.push(name);
-        }
-    }
+    if (cookieDomain.charAt(0) !== '.')
+        return resourceDomain === cookieDomain;
+    return !!resourceDomain.match(new RegExp("^([^\\.]+\\.)?" + cookieDomain.substring(1).escapeForRegExp() + "$"), "i");
 }
 
-WebInspector.CSSStyleDeclaration.parseStyle = function(payload)
-{
-    return new WebInspector.CSSStyleDeclaration(payload);
-}
+WebInspector.EventListeners = {}
 
-WebInspector.CSSStyleDeclaration.parseRule = function(payload)
+WebInspector.EventListeners.getEventListenersForNodeAsync = function(node, callback)
 {
-    var rule = {};
-    rule.id = payload.id;
-    rule.selectorText = payload.selectorText;
-    rule.style = new WebInspector.CSSStyleDeclaration(payload.style);
-    rule.style.parentRule = rule;
-    rule.isUserAgent = payload.isUserAgent;
-    rule.isUser = payload.isUser;
-    rule.isViaInspector = payload.isViaInspector;
-    if (payload.parentStyleSheet)
-        rule.parentStyleSheet = { href: payload.parentStyleSheet.href };
-
-    return rule;
-}
-
-WebInspector.CSSStyleDeclaration.prototype = {
-    getPropertyValue: function(name)
-    {
-        var property = this._propertyMap[name];
-        return property ? property.value : "";
-    },
-
-    getPropertyPriority: function(name)
-    {
-        var property = this._propertyMap[name];
-        return property ? property.priority : "";
-    },
-
-    getPropertyShorthand: function(name)
-    {
-        var property = this._propertyMap[name];
-        return property ? property.shorthand : "";
-    },
-
-    isPropertyImplicit: function(name)
-    {
-        var property = this._propertyMap[name];
-        return property ? property.implicit : "";
-    },
-
-    styleTextWithShorthands: function()
-    {
-        var cssText = "";
-        var foundProperties = {};
-        for (var i = 0; i < this.length; ++i) {
-            var individualProperty = this[i];
-            var shorthandProperty = this.getPropertyShorthand(individualProperty);
-            var propertyName = (shorthandProperty || individualProperty);
-
-            if (propertyName in foundProperties)
-                continue;
-
-            if (shorthandProperty) {
-                var value = this.getPropertyValue(shorthandProperty);
-                var priority = this.getShorthandPriority(shorthandProperty);
-            } else {
-                var value = this.getPropertyValue(individualProperty);
-                var priority = this.getPropertyPriority(individualProperty);
-            }
-
-            foundProperties[propertyName] = true;
-
-            cssText += propertyName + ": " + value;
-            if (priority)
-                cssText += " !" + priority;
-            cssText += "; ";
-        }
-
-        return cssText;
-    },
-
-    getLonghandProperties: function(name)
-    {
-        return this._longhandProperties[name] || [];
-    },
-
-    getShorthandValue: function(shorthandProperty)
-    {
-        return this._shorthandValues[shorthandProperty];
-    },
-
-    getShorthandPriority: function(shorthandProperty)
-    {
-        var priority = this.getPropertyPriority(shorthandProperty);
-        if (priority)
-            return priority;
-
-        var longhands = this._longhandProperties[shorthandProperty];
-        return longhands ? this.getPropertyPriority(longhands[0]) : null;
-    }
+    if (!node)
+        return;
+    InspectorBackend.getEventListenersForNode(node.id, callback);
 }
 
 WebInspector.attributesUpdated = function()
@@ -619,6 +531,11 @@ WebInspector.attributesUpdated = function()
     this.domAgent._attributesUpdated.apply(this.domAgent, arguments);
 }
 
+WebInspector.characterDataModified = function()
+{
+    this.domAgent._characterDataModified.apply(this.domAgent, arguments);
+}
+
 WebInspector.setDocument = function()
 {
     this.domAgent._setDocument.apply(this.domAgent, arguments);
@@ -648,11 +565,3 @@ WebInspector.childNodeRemoved = function()
 {
     this.domAgent._childNodeRemoved.apply(this.domAgent, arguments);
 }
-
-WebInspector.didGetCookies = WebInspector.Callback.processCallback;
-WebInspector.didGetChildNodes = WebInspector.Callback.processCallback;
-WebInspector.didPerformSearch = WebInspector.Callback.processCallback;
-WebInspector.didApplyDomChange = WebInspector.Callback.processCallback;
-WebInspector.didRemoveAttribute = WebInspector.Callback.processCallback;
-WebInspector.didSetTextNodeValue = WebInspector.Callback.processCallback;
-WebInspector.didGetEventListenersForNode = WebInspector.Callback.processCallback;