Skip to content

Commit 5eaa8d2

Browse files
author
David Håsäther
committed
Beta implementation for DFL-2826: Implement UI for return value list.
1 parent be0789e commit 5eaa8d2

File tree

9 files changed

+238
-4
lines changed

9 files changed

+238
-4
lines changed

src/ecma-debugger/action_handler.js

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,13 @@
3232
}
3333
};
3434

35+
window.eventHandlers.click["goto-script-line"] = function(event, target)
36+
{
37+
var script_id = Number(event.target.getAttribute("data-script-id"));
38+
var script_line = Number(event.target.getAttribute("data-script-line"));
39+
views.js_source.show_and_flash_line(script_id, script_line);
40+
};
41+
3542
window.eventHandlers.click['expand-value'] = function(event, target)
3643
{
3744
var

src/ecma-debugger/objectinspection.6.0/baseview.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -56,4 +56,4 @@ cls.EcmascriptDebugger["6.0"].InspectionBaseView = function()
5656

5757
}
5858

59-
cls.EcmascriptDebugger["6.0"].InspectionBaseView.prototype = ViewBase;
59+
cls.EcmascriptDebugger["6.0"].InspectionBaseView.prototype = ViewBase;

src/ecma-debugger/objectinspection.6.0/templates.js

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -278,7 +278,8 @@
278278
"/>" +
279279
"<key " + (has_match ? "" : " class='no-match'") +
280280
"data-spec='dom#" + esc_name + "'" + editable(prop) +
281-
">" + esc_name + "</key> " +
281+
">" + esc_name + "</key>" +
282+
(esc_name ? " " : "") +
282283
"<value class='object" + (has_match ? "" : " no-match") + "' " +
283284
"data-spec='dom#" + value + "' " +
284285
"data-tooltip='" + TOOLTIP_NAME + "' >" + value + "</value>"

src/ecma-debugger/stop_at.js

Lines changed: 26 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -54,6 +54,7 @@ cls.EcmascriptDebugger["6.0"].StopAt = function()
5454
var runtime_id = '';
5555

5656
var callstack = [];
57+
var return_values = [];
5758

5859
var __script_ids_in_callstack = [];
5960

@@ -132,6 +133,11 @@ cls.EcmascriptDebugger["6.0"].StopAt = function()
132133
return callstack; // should be copied
133134
}
134135

136+
this.get_return_values = function()
137+
{
138+
return return_values;
139+
};
140+
135141
this.get_script_ids_in_callstack = function()
136142
{
137143
return __script_ids_in_callstack;
@@ -185,6 +191,7 @@ cls.EcmascriptDebugger["6.0"].StopAt = function()
185191
{
186192
const
187193
FRAME_LIST = 0,
194+
RETURN_VALUE_LIST = 1,
188195
// sub message BacktraceFrame
189196
FUNCTION_ID = 0,
190197
ARGUMENT_OBJECT = 1,
@@ -213,6 +220,7 @@ cls.EcmascriptDebugger["6.0"].StopAt = function()
213220
var line_number = 0;
214221
callstack = [];
215222
__script_ids_in_callstack = [];
223+
216224
for( ; frame = _frames[i]; i++ )
217225
{
218226
line_number = frame[LINE_NUMBER];
@@ -242,7 +250,21 @@ cls.EcmascriptDebugger["6.0"].StopAt = function()
242250
}
243251
__script_ids_in_callstack[i] = frame[SCRIPT_ID];
244252
}
245-
253+
254+
var return_value_list = message[RETURN_VALUE_LIST];
255+
if (return_value_list)
256+
{
257+
return_values = return_value_list.map(function(retval) {
258+
return {
259+
value: retval[0],
260+
function_from: retval[1],
261+
position_from: retval[2],
262+
position_to: retval[3],
263+
rt_id: stop_at.runtime_id
264+
};
265+
});
266+
}
267+
246268
if( cur_inspection_type != 'frame' )
247269
{
248270
messages.post('active-inspection-type', {inspection_type: 'frame'});
@@ -303,6 +325,7 @@ cls.EcmascriptDebugger["6.0"].StopAt = function()
303325
{
304326
this._clear_stop_at_error();
305327
callstack = [];
328+
return_values = [];
306329
__script_ids_in_callstack = [];
307330
runtimes.setObserve(stopAt.runtime_id, mode != 'run');
308331
messages.post('frame-selected', {frame_index: -1});
@@ -323,6 +346,7 @@ cls.EcmascriptDebugger["6.0"].StopAt = function()
323346
{
324347
this._clear_stop_at_error();
325348
callstack = [];
349+
return_values = [];
326350
__script_ids_in_callstack = [];
327351
messages.post('frame-selected', {frame_index: -1});
328352
__controls_enabled = false;
@@ -583,4 +607,4 @@ cls.EcmascriptDebugger["6.0"].StopAt = function()
583607
this._bps = window.cls.Breakpoints.get_instance();
584608

585609

586-
}
610+
}

src/ecma-debugger/templates.js

Lines changed: 147 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -322,6 +322,153 @@
322322
].concat( is_top ? ["class", "selected"] : [] );
323323
}
324324

325+
this.return_values = function(values)
326+
{
327+
return ["div", values.map(this.return_value), "class", "return-values"];
328+
};
329+
330+
this.return_value = function(retval)
331+
{
332+
// TODO: move constants
333+
var UNDEFINED = 0;
334+
var NULL = 1;
335+
var TRUE = 2;
336+
var FALSE = 3;
337+
var NAN = 4;
338+
var PLUS_INFINITY = 5;
339+
var MINUS_INFINITY = 6;
340+
var NUMBER = 7;
341+
var STRING = 8;
342+
var OBJECT = 9;
343+
var types = {};
344+
types[UNDEFINED] = "undefined";
345+
types[NULL] = "null";
346+
types[TRUE] = "boolean";
347+
types[FALSE] = "boolean";
348+
types[NAN] = "number";
349+
types[PLUS_INFINITY] = "number";
350+
types[MINUS_INFINITY] = "number";
351+
types[NUMBER] = "number";
352+
types[STRING] = "string";
353+
var names = {};
354+
names[TRUE] = "true";
355+
names[FALSE] = "false";
356+
names[NAN] = "NaN";
357+
names[PLUS_INFINITY] = "Infinity";
358+
names[MINUS_INFINITY] = "-Infinity";
359+
360+
var value = "";
361+
var type = types[retval.value[0]];
362+
switch (retval.value[0])
363+
{
364+
case UNDEFINED:
365+
case NULL:
366+
value =
367+
"<item>" +
368+
"<value class='" + type + "'>" + type + "</value>" +
369+
"</item>";
370+
break;
371+
372+
case TRUE:
373+
case FALSE:
374+
case NAN:
375+
case PLUS_INFINITY:
376+
case MINUS_INFINITY:
377+
value =
378+
"<item>" +
379+
"<value class='" + type + "'>" + names[retval.value[0]] + "</value>" +
380+
"</item>"
381+
break;
382+
383+
case NUMBER:
384+
value =
385+
"<item>" +
386+
"<value class='" + type + "'>" + String(retval.value[1]) + "</value>" +
387+
"</item>"
388+
break;
389+
390+
case STRING:
391+
var MAX_VALUE_LENGTH = 30;
392+
var val = retval.value[2];
393+
short_val = val.length > MAX_VALUE_LENGTH ?
394+
val.slice(0, MAX_VALUE_LENGTH) + '…' : '';
395+
val = helpers.escapeTextHtml(val).replace(/'/g, '&#39;');
396+
if (short_val)
397+
{
398+
value =
399+
"<item>" +
400+
"<input type='button' handler='expand-value' class='folder-key'/>" +
401+
"<value class='" + type + "' data-value='\"" + val + "\"'>" +
402+
"\"" + helpers.escapeTextHtml(short_val) + "\"" +
403+
"</value>" +
404+
"</item>"
405+
}
406+
else
407+
{
408+
value =
409+
"<item>" +
410+
"<value class='" + type + "'>\"" + val + "\"</value>" +
411+
"</item>"
412+
}
413+
break;
414+
415+
case OBJECT:
416+
var object = retval.value[3/*OBJECT*/];
417+
var name = object[4/*CLASS_NAME*/] === "Function" && !object[5]
418+
? ui_strings.S_ANONYMOUS_FUNCTION_NAME
419+
: object[5];
420+
var model = new cls.InspectableJSObject(retval.rt_id,
421+
object[0/*OBJECT_ID*/],
422+
name,
423+
object[4/*CLASS_NAME*/]);
424+
var value = window.templates.inspected_js_object(model);
425+
break;
426+
}
427+
428+
var from_script_id = retval.position_from[0];
429+
var from_uri = from_script_id && runtimes.getScript(from_script_id)
430+
? (runtimes.getScript(from_script_id).uri || runtimes.getRuntime(retval.rt_id).uri)
431+
: "<unknown script>";
432+
var to_script_id = retval.position_to[0];
433+
var to_uri = to_script_id && runtimes.getScript(to_script_id)
434+
? (runtimes.getScript(to_script_id).uri || runtimes.getRuntime(retval.rt_id).uri)
435+
: "<unknown script>";
436+
437+
var object = retval.function_from;
438+
var model = new cls.InspectableJSObject(retval.rt_id,
439+
object[0/*OBJECT_ID*/],
440+
retval.function_from[5] || ui_strings.S_ANONYMOUS_FUNCTION_NAME,
441+
object[4/*CLASS_NAME*/]);
442+
var func_name = window.templates.inspected_js_object(model);
443+
444+
return [
445+
["div",
446+
["span",
447+
"↱",
448+
"class", "return-value-arrow return-value-arrow-from",
449+
"handler", "goto-script-line",
450+
"title", "Returned from " + window.helpers.basename(from_uri) + ":" + retval.position_from[1],
451+
"data-script-id", String(retval.position_from[0]),
452+
"data-script-line", String(retval.position_from[1])
453+
],
454+
[func_name],
455+
"class", "return-function-from"
456+
],
457+
["div",
458+
["span",
459+
"↳",
460+
"class", "return-value-arrow return-value-arrow-to",
461+
"handler", "goto-script-line",
462+
"title", "Returned to " + window.helpers.basename(to_uri) + ":" + retval.position_to[1],
463+
"data-script-id", String(retval.position_to[0]),
464+
"data-script-line", String(retval.position_to[1])
465+
],
466+
[value],
467+
"class", "return-value"
468+
]
469+
];
470+
};
471+
325472
this.configStopAt = function(config)
326473
{
327474
var ret =["ul"];

src/ecma-debugger/views.js

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -133,8 +133,13 @@ cls.CallstackView = function(id, name, container_class)
133133
{
134134
__clear_timeout = clearTimeout( __clear_timeout );
135135
}
136+
137+
136138
var _frames = stop_at.getFrames(), frame = null, i = 0;
139+
var return_values = stop_at.get_return_values();
137140
list.innerHTML = _frames.length ? "" : not_stopped_content;
141+
if (return_values.length)
142+
list.render(templates.return_values(return_values));
138143
for( ; frame = _frames[i]; i++)
139144
{
140145
list.render(templates.frame(frame, i == this._selected_frame));

src/ui-images/arrow_roundl.png

213 Bytes
Loading

src/ui-images/arrow_tail.png

205 Bytes
Loading

src/ui-style/debugger_style.css

Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1562,3 +1562,53 @@ d
15621562
{
15631563
margin: 0;
15641564
}
1565+
1566+
/* temporary stuff */
1567+
.return-values
1568+
{
1569+
border-bottom: 1px solid #D7D7D7;
1570+
margin-bottom: 5px;
1571+
}
1572+
1573+
.return-value
1574+
{
1575+
margin-bottom: 5px;
1576+
white-space: nowrap;
1577+
margin-left: 17px;
1578+
}
1579+
1580+
.return-function-from > examine-objects,
1581+
.return-value > examine-objects,
1582+
.return-value > item
1583+
{
1584+
display: inline-block;
1585+
padding: 0;
1586+
}
1587+
1588+
/* TODO: use another template instead */
1589+
.return-function-from .folder-key
1590+
{
1591+
display: none;
1592+
}
1593+
1594+
.return-value-arrow
1595+
{
1596+
display: inline-block;
1597+
vertical-align: top;
1598+
width: 15px;
1599+
height: 16px;
1600+
background-repeat: no-repeat;
1601+
cursor: pointer;
1602+
content: "";
1603+
}
1604+
1605+
.return-function-from
1606+
{
1607+
background: transparent url("../ui-images/arrow_roundl.png") 0 50% no-repeat;
1608+
}
1609+
1610+
.return-value-arrow-to
1611+
{
1612+
background: transparent url("../ui-images/arrow_tail.png") 0 50% no-repeat;
1613+
}
1614+

0 commit comments

Comments
 (0)