Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1457)

Side by Side Diff: Source/devtools/front_end/components/ObjectPropertiesSection.js

Issue 826713005: DevTools: Highlight changed scope variables as they change (Closed) Base URL: https://chromium.googlesource.com/chromium/blink.git@master
Patch Set: Created 5 years, 11 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « no previous file | Source/devtools/front_end/sources/WatchExpressionsSidebarPane.js » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 /* 1 /*
2 * Copyright (C) 2008 Apple Inc. All Rights Reserved. 2 * Copyright (C) 2008 Apple Inc. All Rights Reserved.
3 * Copyright (C) 2009 Joseph Pecoraro 3 * Copyright (C) 2009 Joseph Pecoraro
4 * 4 *
5 * Redistribution and use in source and binary forms, with or without 5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions 6 * modification, are permitted provided that the following conditions
7 * are met: 7 * are met:
8 * 1. Redistributions of source code must retain the above copyright 8 * 1. Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer. 9 * notice, this list of conditions and the following disclaimer.
10 * 2. Redistributions in binary form must reproduce the above copyright 10 * 2. Redistributions in binary form must reproduce the above copyright
(...skipping 26 matching lines...) Expand all
37 */ 37 */
38 WebInspector.ObjectPropertiesSection = function(object, title, subtitle, emptyPl aceholder, ignoreHasOwnProperty, extraProperties, treeElementConstructor) 38 WebInspector.ObjectPropertiesSection = function(object, title, subtitle, emptyPl aceholder, ignoreHasOwnProperty, extraProperties, treeElementConstructor)
39 { 39 {
40 this._emptyPlaceholder = emptyPlaceholder; 40 this._emptyPlaceholder = emptyPlaceholder;
41 this.object = object; 41 this.object = object;
42 this.ignoreHasOwnProperty = ignoreHasOwnProperty; 42 this.ignoreHasOwnProperty = ignoreHasOwnProperty;
43 this.extraProperties = extraProperties; 43 this.extraProperties = extraProperties;
44 this.treeElementConstructor = treeElementConstructor || WebInspector.ObjectP ropertyTreeElement; 44 this.treeElementConstructor = treeElementConstructor || WebInspector.ObjectP ropertyTreeElement;
45 this.editable = true; 45 this.editable = true;
46 this.skipProto = false; 46 this.skipProto = false;
47 this.pane = {}; // set in ScopeChainSidebarPane
aandrey 2015/01/12 14:50:35 This should be better encapsulated. The ObjectProp
47 48
48 WebInspector.Section.call(this, title || "", subtitle); 49 WebInspector.Section.call(this, title || "", subtitle);
49 } 50 }
50 51
51 /** @const */ 52 /** @const */
52 WebInspector.ObjectPropertiesSection._arrayLoadThreshold = 100; 53 WebInspector.ObjectPropertiesSection._arrayLoadThreshold = 100;
53 54
54 WebInspector.ObjectPropertiesSection.prototype = { 55 WebInspector.ObjectPropertiesSection.prototype = {
55 enableContextMenu: function() 56 enableContextMenu: function()
56 { 57 {
(...skipping 30 matching lines...) Expand all
87 if (!properties) 88 if (!properties)
88 return; 89 return;
89 this.updateProperties(properties, internalProperties); 90 this.updateProperties(properties, internalProperties);
90 } 91 }
91 92
92 WebInspector.RemoteObject.loadFromObject(this.object, !!this.ignoreHasOw nProperty, callback.bind(this)); 93 WebInspector.RemoteObject.loadFromObject(this.object, !!this.ignoreHasOw nProperty, callback.bind(this));
93 }, 94 },
94 95
95 updateProperties: function(properties, internalProperties, rootTreeElementCo nstructor, rootPropertyComparer) 96 updateProperties: function(properties, internalProperties, rootTreeElementCo nstructor, rootPropertyComparer)
96 { 97 {
98 // Delete the cached last descriptions of all propertyIdentifiers
99 // did were not preset when the debugee was suspended last time
100 if (this.pane && this.pane._lastDescriptions && this.pane._propertyIdent ifiers)
101 for (var pi in this.pane._lastDescriptions) {
102 if (!(pi in this.pane._propertyIdentifiers))
103 // Delete the properties that no longer exist
104 delete this.pane._lastDescriptions[pi];
105 }
106
107 // start with empty propertyIdentifiers cache
108 // this will get populated as the tree elemnts are
109 // shown
110 if (this.pane)
111 this.pane._propertyIdentifiers = {};
112
97 if (!rootTreeElementConstructor) 113 if (!rootTreeElementConstructor)
98 rootTreeElementConstructor = this.treeElementConstructor; 114 rootTreeElementConstructor = this.treeElementConstructor;
99 115
100 if (!rootPropertyComparer) 116 if (!rootPropertyComparer)
101 rootPropertyComparer = WebInspector.ObjectPropertiesSection.CompareP roperties; 117 rootPropertyComparer = WebInspector.ObjectPropertiesSection.CompareP roperties;
102 118
103 if (this.extraProperties) { 119 if (this.extraProperties) {
104 for (var i = 0; i < this.extraProperties.length; ++i) 120 for (var i = 0; i < this.extraProperties.length; ++i)
105 properties.push(this.extraProperties[i]); 121 properties.push(this.extraProperties[i]);
106 } 122 }
(...skipping 64 matching lines...) Expand 10 before | Expand all | Expand 10 after
171 if ((this.property.writable || this.property.setter) && event.target.isS elfOrDescendant(editableElement)) 187 if ((this.property.writable || this.property.setter) && event.target.isS elfOrDescendant(editableElement))
172 this.startEditing(event); 188 this.startEditing(event);
173 return false; 189 return false;
174 }, 190 },
175 191
176 /** 192 /**
177 * @override 193 * @override
178 */ 194 */
179 onattach: function() 195 onattach: function()
180 { 196 {
197 // record the propertyIdentifier
198 if (this.propertyPath() && this.treeOutline.section.pane && this.treeOut line.section.pane._propertyIdentifiers)
199 this.treeOutline.section.pane._propertyIdentifiers[this.propertyPath ()] = 1;
200
181 this.update(); 201 this.update();
182 }, 202 },
183 203
184 update: function() 204 update: function()
185 { 205 {
186 this.nameElement = createElementWithClass("span", "name"); 206 this.nameElement = createElementWithClass("span", "name");
187 var name = this.property.name; 207 var name = this.property.name;
188 if (/^\s|\s$|^$|\n/.test(name)) 208 if (/^\s|\s$|^$|\n/.test(name))
189 this.nameElement.createTextChildren("\"", name.replace(/\n/g, "\u21B 5"), "\""); 209 this.nameElement.createTextChildren("\"", name.replace(/\n/g, "\u21B 5"), "\"");
190 else 210 else
191 this.nameElement.textContent = name; 211 this.nameElement.textContent = name;
192 if (!this.property.enumerable) 212 if (!this.property.enumerable)
193 this.nameElement.classList.add("dimmed"); 213 this.nameElement.classList.add("dimmed");
194 if (this.property.isAccessorProperty()) 214 if (this.property.isAccessorProperty())
195 this.nameElement.classList.add("properties-accessor-property-name"); 215 this.nameElement.classList.add("properties-accessor-property-name");
196 if (this.property.symbol) 216 if (this.property.symbol)
197 this.nameElement.addEventListener("contextmenu", this._contextMenuFi red.bind(this, this.property.symbol), false); 217 this.nameElement.addEventListener("contextmenu", this._contextMenuFi red.bind(this, this.property.symbol), false);
198 218
199 var separatorElement = createElementWithClass("span", "separator"); 219 var separatorElement = createElementWithClass("span", "separator");
200 separatorElement.textContent = ": "; 220 separatorElement.textContent = ": ";
201 221
202 if (this.property.value) { 222 if (this.property.value) {
203 this.valueElement = createElementWithClass("span", "value"); 223 this.valueElement = createElementWithClass("span", "value");
204 var type = this.property.value.type; 224 var type = this.property.value.type;
205 var subtype = this.property.value.subtype; 225 var subtype = this.property.value.subtype;
226 // detect if the propertyIdentifier was shown when the debugee was s uspended last time
227 var hadProperty = true;
228 if (this.propertyPath() && this.treeOutline.section && this.treeOutl ine.section.pane)
229 // not a first suspension
230 if (this.treeOutline.section.pane._lastDescriptions)
231 hadProperty = (this.treeOutline.section.pane._lastDescriptio ns[this.propertyPath()] != undefined);
232 else {
233 // first suspension
234 this.treeOutline.section.pane._lastDescriptions = {};
235 hadProperty = false;
236 }
237
238 var oldDescription;
239
240 if (this.propertyPath() && this.treeOutline.section && this.treeOutl ine.section.pane && this.treeOutline.section.pane._lastDescriptions)
241 // retrieve the description from last suspension
242 oldDescription = this.treeOutline.section.pane._lastDescriptions [this.propertyPath()];
243
244 // description now
206 var description = this.property.value.description; 245 var description = this.property.value.description;
246
247 var descriptionToCompare = (type + ":" +
248 (subtype? subtype : "") + ":" + /* (this.property.value.objectId ? this.property.value.objectId : "") + ":" + */ description);
249 // determine if it has it changed only if description is initialized
250 // this handles the case when the variable came into scope but
251 // was not initialized
252 var descriptionChanged = false;
253 if (hadProperty)
254 descriptionChanged = (descriptionToCompare != oldDescription);
255 else
256 descriptionChanged = true;
257
258 if (this.propertyPath() && this.treeOutline.section && this.treeOutl ine.section.pane && this.treeOutline.section.pane._lastDescriptions)
259 this.treeOutline.section.pane._lastDescriptions[this.propertyPat h()] = descriptionToCompare;
260
207 var prefix; 261 var prefix;
208 var valueText; 262 var valueText;
209 var suffix; 263 var suffix;
210 if (this.property.wasThrown) { 264 if (this.property.wasThrown) {
211 prefix = "[Exception: "; 265 prefix = "[Exception: ";
212 valueText = description; 266 valueText = description;
213 suffix = "]"; 267 suffix = "]";
214 } else if (type === "string" && typeof description === "string") { 268 } else if (type === "string" && typeof description === "string") {
215 // Render \n as a nice unicode cr symbol. 269 // Render \n as a nice unicode cr symbol.
216 prefix = "\""; 270 prefix = "\"";
(...skipping 16 matching lines...) Expand all
233 } else { 287 } else {
234 var numberParts = valueText.split("e"); 288 var numberParts = valueText.split("e");
235 var mantissa = this.valueElement.createChild("span", "scientific -notation-mantissa"); 289 var mantissa = this.valueElement.createChild("span", "scientific -notation-mantissa");
236 mantissa.textContent = numberParts[0]; 290 mantissa.textContent = numberParts[0];
237 var exponent = this.valueElement.createChild("span", "scientific -notation-exponent"); 291 var exponent = this.valueElement.createChild("span", "scientific -notation-exponent");
238 exponent.textContent = "e" + numberParts[1]; 292 exponent.textContent = "e" + numberParts[1];
239 this.valueElement.classList.add("scientific-notation-number"); 293 this.valueElement.classList.add("scientific-notation-number");
240 this.listItemElement.classList.add("hbox"); 294 this.listItemElement.classList.add("hbox");
241 } 295 }
242 296
297 if (descriptionChanged) {
298 this.valueElement.classList.add("highlighted-search-result");
299 if (!hadProperty)
300 // new - highlight name also
301 this.nameElement.classList.add("highlighted-search-result");
302 }
303
243 if (this.property.wasThrown) 304 if (this.property.wasThrown)
244 this.valueElement.classList.add("error"); 305 this.valueElement.classList.add("error");
245 if (subtype || type) 306 if (subtype || type)
246 this.valueElement.classList.add("console-formatted-" + (subtype || type)); 307 this.valueElement.classList.add("console-formatted-" + (subtype || type));
247 308
248 this.valueElement.addEventListener("contextmenu", this._contextMenuF ired.bind(this, this.property.value), false); 309 this.valueElement.addEventListener("contextmenu", this._contextMenuF ired.bind(this, this.property.value), false);
249 if (type === "object" && subtype === "node" && description) { 310 if (type === "object" && subtype === "node" && description) {
250 WebInspector.DOMPresentationUtils.createSpansForNodeTitle(this.v alueElement, description); 311 WebInspector.DOMPresentationUtils.createSpansForNodeTitle(this.v alueElement, description);
251 this.valueElement.addEventListener("mousemove", this._mouseMove. bind(this), false); 312 this.valueElement.addEventListener("mousemove", this._mouseMove. bind(this), false);
252 this.valueElement.addEventListener("mouseleave", this._mouseLeav e.bind(this), false); 313 this.valueElement.addEventListener("mouseleave", this._mouseLeav e.bind(this), false);
(...skipping 844 matching lines...) Expand 10 before | Expand all | Expand 10 after
1097 { 1158 {
1098 WebInspector.TextPrompt.call(this, WebInspector.ExecutionContextSelector.com pletionsForTextPromptInCurrentContext); 1159 WebInspector.TextPrompt.call(this, WebInspector.ExecutionContextSelector.com pletionsForTextPromptInCurrentContext);
1099 this.setSuggestBoxEnabled(true); 1160 this.setSuggestBoxEnabled(true);
1100 if (renderAsBlock) 1161 if (renderAsBlock)
1101 this.renderAsBlock(); 1162 this.renderAsBlock();
1102 } 1163 }
1103 1164
1104 WebInspector.ObjectPropertyPrompt.prototype = { 1165 WebInspector.ObjectPropertyPrompt.prototype = {
1105 __proto__: WebInspector.TextPrompt.prototype 1166 __proto__: WebInspector.TextPrompt.prototype
1106 } 1167 }
OLDNEW
« no previous file with comments | « no previous file | Source/devtools/front_end/sources/WatchExpressionsSidebarPane.js » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698