OLD | NEW |
---|---|
1 // Copyright (c) 2009 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2009 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 /** | 5 /** |
6 * @fileoverview Javascript that is being injected into the inspectable page | 6 * @fileoverview Javascript that is being injected into the inspectable page |
7 * while debugging. | 7 * while debugging. |
8 */ | 8 */ |
9 goog.require('goog.json'); | 9 goog.require('goog.json'); |
10 goog.provide('devtools.Injected'); | 10 goog.provide('devtools.Injected'); |
(...skipping 93 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
104 * Returns style information that is used in devtools.js. | 104 * Returns style information that is used in devtools.js. |
105 * @param {Node} node Node to get prorotypes for. | 105 * @param {Node} node Node to get prorotypes for. |
106 * @param {boolean} authorOnly Determines whether only author styles need to | 106 * @param {boolean} authorOnly Determines whether only author styles need to |
107 * be added. | 107 * be added. |
108 * @return {string} Style collection descriptor. | 108 * @return {string} Style collection descriptor. |
109 */ | 109 */ |
110 devtools.Injected.prototype.getStyles = function(node, authorOnly) { | 110 devtools.Injected.prototype.getStyles = function(node, authorOnly) { |
111 if (!node.nodeType == Node.ELEMENT_NODE) { | 111 if (!node.nodeType == Node.ELEMENT_NODE) { |
112 return {}; | 112 return {}; |
113 } | 113 } |
114 var matchedRules = window.getMatchedCSSRules(node, '', authorOnly); | 114 var matchedRules = window.getMatchedCSSRules(node, '', false); |
115 var matchedCSSRulesObj = []; | 115 var matchedCSSRulesObj = []; |
116 for (var i = 0; matchedRules && i < matchedRules.length; ++i) { | 116 for (var i = 0; matchedRules && i < matchedRules.length; ++i) { |
117 var rule = matchedRules[i]; | 117 var rule = matchedRules[i]; |
118 var style = this.serializeStyle_(rule.style); | 118 var parentStyleSheet = rule.parentStyleSheet; |
119 var isUserAgent = parentStyleSheet && !parentStyleSheet.ownerNode && | |
120 !parentStyleSheet.href; | |
121 var isUser = parentStyleSheet && parentStyleSheet.ownerNode && | |
122 parentStyleSheet.ownerNode.nodeName == '#document'; | |
123 | |
124 var style = this.serializeStyle_(rule.style, !isUserAgent && !isUser); | |
119 var ruleValue = { | 125 var ruleValue = { |
120 'selector' : rule.selectorText, | 126 'selector' : rule.selectorText, |
121 'style' : style | 127 'style' : style |
122 }; | 128 }; |
123 if (rule.parentStyleSheet) { | 129 if (parentStyleSheet) { |
124 ruleValue['parentStyleSheet'] = { | 130 ruleValue['parentStyleSheet'] = { |
125 'href' : rule.parentStyleSheet.href, | 131 'href' : parentStyleSheet.href, |
126 'ownerNodeName' : rule.parentStyleSheet.ownerNode ? | 132 'ownerNodeName' : parentStyleSheet.ownerNode ? |
127 rule.parentStyleSheet.ownerNode.name : null | 133 parentStyleSheet.ownerNode.name : null |
128 }; | 134 }; |
129 } | 135 } |
130 var parentStyleSheetHref = (rule.parentStyleSheet ? | |
131 rule.parentStyleSheet.href : undefined); | |
132 var parentStyleSheetOwnerNodeName; | |
133 if (rule.parentStyleSheet && rule.parentStyleSheet.ownerNode) { | |
134 parentStyleSheetOwnerNodeName = rule.parentStyleSheet.ownerNode.name; | |
135 } | |
136 matchedCSSRulesObj.push(ruleValue); | 136 matchedCSSRulesObj.push(ruleValue); |
137 } | 137 } |
138 | 138 |
139 var attributeStyles = {}; | 139 var attributeStyles = {}; |
140 var attributes = node.attributes; | 140 var attributes = node.attributes; |
141 for (var i = 0; attributes && i < attributes.length; ++i) { | 141 for (var i = 0; attributes && i < attributes.length; ++i) { |
142 if (attributes[i].style) { | 142 if (attributes[i].style) { |
143 attributeStyles[attributes[i].name] = | 143 attributeStyles[attributes[i].name] = |
144 this.serializeStyle_(attributes[i].style); | 144 this.serializeStyle_(attributes[i].style, true); |
145 } | 145 } |
146 } | 146 } |
147 | |
148 var result = { | 147 var result = { |
149 'inlineStyle' : this.serializeStyle_(node.style), | 148 'inlineStyle' : this.serializeStyle_(node.style, true), |
150 'computedStyle' : this.serializeStyle_( | 149 'computedStyle' : this.serializeStyle_( |
151 window.getComputedStyle(node, '')), | 150 window.getComputedStyle(node, '')), |
152 'matchedCSSRules' : matchedCSSRulesObj, | 151 'matchedCSSRules' : matchedCSSRulesObj, |
153 'styleAttributes' : attributeStyles | 152 'styleAttributes' : attributeStyles |
154 }; | 153 }; |
155 return result; | 154 return result; |
156 }; | 155 }; |
157 | 156 |
158 | 157 |
159 /** | 158 /** |
(...skipping 22 matching lines...) Expand all Loading... | |
182 } | 181 } |
183 return null; | 182 return null; |
184 }; | 183 }; |
185 | 184 |
186 | 185 |
187 | 186 |
188 | 187 |
189 /** | 188 /** |
190 * Converts given style into serializable object. | 189 * Converts given style into serializable object. |
191 * @param {CSSStyleDeclaration} style Style to serialize. | 190 * @param {CSSStyleDeclaration} style Style to serialize. |
191 * @param {boolean} opt_bind Determins whether this style should be bound. | |
192 * @return {Array<Object>} Serializable object. | 192 * @return {Array<Object>} Serializable object. |
193 * @private | 193 * @private |
194 */ | 194 */ |
195 devtools.Injected.prototype.serializeStyle_ = function(style) { | 195 devtools.Injected.prototype.serializeStyle_ = function(style, opt_bind) { |
196 if (!style) { | 196 if (!style) { |
197 return []; | 197 return []; |
198 } | 198 } |
199 if (!style.__id) { | 199 var id = style.__id; |
200 style.__id = this.lastStyleId_++; | 200 if (opt_bind && !id) { |
201 id = style.__id = this.lastStyleId_++; | |
201 this.styles_.push(style); | 202 this.styles_.push(style); |
202 } | 203 } |
203 var result = [ | 204 var result = [ |
204 style.__id, | 205 id, |
205 style.__disabledProperties, | 206 style.__disabledProperties, |
206 style.__disabledPropertyValues, | 207 style.__disabledPropertyValues, |
207 style.__disabledPropertyPriorities | 208 style.__disabledPropertyPriorities |
208 ]; | 209 ]; |
209 for (var i = 0; i < style.length; ++i) { | 210 for (var i = 0; i < style.length; ++i) { |
210 var name = style[i]; | 211 var name = style[i]; |
211 result.push([ | 212 result.push([ |
212 name, | 213 name, |
213 style.getPropertyPriority(name), | 214 style.getPropertyPriority(name), |
214 style.isPropertyImplicit(name), | 215 style.isPropertyImplicit(name), |
(...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
263 | 264 |
264 delete style.__disabledProperties[name]; | 265 delete style.__disabledProperties[name]; |
265 delete style.__disabledPropertyValues[name]; | 266 delete style.__disabledPropertyValues[name]; |
266 delete style.__disabledPropertyPriorities[name]; | 267 delete style.__disabledPropertyPriorities[name]; |
267 } | 268 } |
268 return true; | 269 return true; |
269 }; | 270 }; |
270 | 271 |
271 | 272 |
272 /** | 273 /** |
273 * Returns longhand proeprties for a given shorthand one. | 274 * Applies given text to a style. |
274 * @param {CSSStyleDeclaration} style Style declaration to use for lookup. | 275 * @param {Node} node Node to get prorotypes for. |
275 * @param {string} shorthandProperty Shorthand property to get longhands for. | 276 * @param {number} styleId Id of style to toggle. |
276 * @return {Array.<string>} Array with longhand properties. | 277 * @param {string} name Style element name. |
277 * @private | 278 * @param {string} styleText New style text. |
279 * @return {boolean} True iff style has been edited successfully. | |
280 */ | |
281 devtools.Injected.prototype.applyStyleText = function(node, styleId, | |
yurys
2009/04/30 09:55:40
wrong parameter alignment here and in some other p
pfeldman
2009/04/30 10:00:16
Lets better stick to this schema!
| |
282 name, styleText) { | |
283 var style = this.getStyleForId_(node, styleId); | |
284 if (!style) { | |
285 return false; | |
286 } | |
287 | |
288 var styleTextLength = this.trimWhitespace_(styleText).length; | |
289 | |
290 // Create a new element to parse the user input CSS. | |
291 var parseElement = document.createElement("span"); | |
292 parseElement.setAttribute("style", styleText); | |
293 | |
294 var tempStyle = parseElement.style; | |
295 if (tempStyle.length || !styleTextLength) { | |
296 // The input was parsable or the user deleted everything, so remove the | |
297 // original property from the real style declaration. If this represents | |
298 // a shorthand remove all the longhand properties. | |
299 if (style.getPropertyShorthand(name)) { | |
300 var longhandProperties = this.getLonghandProperties_(style, name); | |
301 for (var i = 0; i < longhandProperties.length; ++i) { | |
302 style.removeProperty(longhandProperties[i]); | |
303 } | |
304 } else { | |
305 style.removeProperty(name); | |
306 } | |
307 } | |
308 if (!tempStyle.length) { | |
309 // The user typed something, but it didn't parse. Just abort and restore | |
310 // the original title for this property. | |
311 return false; | |
312 } | |
313 | |
314 // Iterate of the properties on the test element's style declaration and | |
315 // add them to the real style declaration. We take care to move shorthands. | |
316 var foundShorthands = {}; | |
317 var uniqueProperties = this.getUniqueStyleProperties_(tempStyle); | |
318 for (var i = 0; i < uniqueProperties.length; ++i) { | |
319 var name = uniqueProperties[i]; | |
320 var shorthand = tempStyle.getPropertyShorthand(name); | |
321 | |
322 if (shorthand && shorthand in foundShorthands) { | |
323 continue; | |
324 } | |
325 | |
326 if (shorthand) { | |
327 var value = this.getShorthandValue_(tempStyle, shorthand); | |
328 var priority = this.getShorthandPriority_(tempStyle, shorthand); | |
329 foundShorthands[shorthand] = true; | |
330 } else { | |
331 var value = tempStyle.getPropertyValue(name); | |
332 var priority = tempStyle.getPropertyPriority(name); | |
333 } | |
334 // Set the property on the real style declaration. | |
335 style.setProperty((shorthand || name), value, priority); | |
336 } | |
337 return true; | |
338 }; | |
339 | |
340 | |
341 /** | |
342 * Taken from utilities.js as is for injected evaluation. | |
278 */ | 343 */ |
279 devtools.Injected.prototype.getLonghandProperties_ = function(style, | 344 devtools.Injected.prototype.getLonghandProperties_ = function(style, |
280 shorthandProperty) { | 345 shorthandProperty) { |
281 var properties = []; | 346 var properties = []; |
282 var foundProperties = {}; | 347 var foundProperties = {}; |
283 | 348 |
284 for (var i = 0; i < style.length; ++i) { | 349 for (var i = 0; i < style.length; ++i) { |
285 var individualProperty = style[i]; | 350 var individualProperty = style[i]; |
286 if (individualProperty in foundProperties || | 351 if (individualProperty in foundProperties || |
287 style.getPropertyShorthand(individualProperty) != shorthandProperty) { | 352 style.getPropertyShorthand(individualProperty) != shorthandProperty) { |
288 continue; | 353 continue; |
289 } | 354 } |
290 foundProperties[individualProperty] = true; | 355 foundProperties[individualProperty] = true; |
291 properties.push(individualProperty); | 356 properties.push(individualProperty); |
292 } | 357 } |
293 return properties; | 358 return properties; |
294 }; | 359 }; |
360 | |
361 | |
362 /** | |
363 * Taken from utilities.js as is for injected evaluation. | |
364 */ | |
365 devtools.Injected.prototype.getShorthandValue_ = function(style, | |
366 shorthandProperty) { | |
367 var value = style.getPropertyValue(shorthandProperty); | |
368 if (!value) { | |
369 // Some shorthands (like border) return a null value, so compute a | |
370 // shorthand value. | |
371 // FIXME: remove this when http://bugs.webkit.org/show_bug.cgi?id=15823 | |
372 // is fixed. | |
373 | |
374 var foundProperties = {}; | |
375 for (var i = 0; i < style.length; ++i) { | |
376 var individualProperty = style[i]; | |
377 if (individualProperty in foundProperties || | |
378 style.getPropertyShorthand(individualProperty) !== | |
379 shorthandProperty) { | |
380 continue; | |
381 } | |
382 | |
383 var individualValue = style.getPropertyValue(individualProperty); | |
384 if (style.isPropertyImplicit(individualProperty) || | |
385 individualValue === "initial") { | |
386 continue; | |
387 } | |
388 | |
389 foundProperties[individualProperty] = true; | |
390 | |
391 if (!value) { | |
392 value = ""; | |
393 } else if (value.length) { | |
394 value += " "; | |
395 } | |
396 value += individualValue; | |
397 } | |
398 } | |
399 return value; | |
400 }; | |
401 | |
402 | |
403 /** | |
404 * Taken from utilities.js as is for injected evaluation. | |
405 */ | |
406 devtools.Injected.prototype.getShorthandPriority_ = function(style, | |
407 shorthandProperty) { | |
408 var priority = style.getPropertyPriority(shorthandProperty); | |
409 if (!priority) { | |
410 for (var i = 0; i < style.length; ++i) { | |
411 var individualProperty = style[i]; | |
412 if (style.getPropertyShorthand(individualProperty) !== | |
413 shorthandProperty) { | |
414 continue; | |
415 } | |
416 priority = style.getPropertyPriority(individualProperty); | |
417 break; | |
418 } | |
419 } | |
420 return priority; | |
421 }; | |
422 | |
423 | |
424 /** | |
425 * Taken from utilities.js as is for injected evaluation. | |
426 */ | |
427 devtools.Injected.prototype.trimWhitespace_ = function(str) { | |
428 return str.replace(/^[\s\xA0]+|[\s\xA0]+$/g, ''); | |
429 }; | |
430 | |
431 | |
432 /** | |
433 * Taken from utilities.js as is for injected evaluation. | |
434 */ | |
435 devtools.Injected.prototype.getUniqueStyleProperties_ = function(style) { | |
436 var properties = []; | |
437 var foundProperties = {}; | |
438 | |
439 for (var i = 0; i < style.length; ++i) { | |
440 var property = style[i]; | |
441 if (property in foundProperties) { | |
442 continue; | |
443 } | |
444 foundProperties[property] = true; | |
445 properties.push(property); | |
446 } | |
447 return properties; | |
448 }; | |
OLD | NEW |