Subversion Repositories Applications.papyrus

Rev

Details | Last modification | View Log | RSS feed

Rev Author Line No. Line
2150 mathias 1
if(!dojo._hasResource["dojo._firebug.firebug"]){ //_hasResource checks added by build. Do not use _hasResource directly in your code.
2
dojo._hasResource["dojo._firebug.firebug"] = true;
3
dojo.provide("dojo._firebug.firebug");
4
 
5
dojo.deprecated = function(/*String*/ behaviour, /*String?*/ extra, /*String?*/ removal){
6
	// summary:
7
	//		Log a debug message to indicate that a behavior has been
8
	//		deprecated.
9
	// extra: Text to append to the message.
10
	// removal:
11
	//		Text to indicate when in the future the behavior will be removed.
12
	var message = "DEPRECATED: " + behaviour;
13
	if(extra){ message += " " + extra; }
14
	if(removal){ message += " -- will be removed in version: " + removal; }
15
	console.debug(message);
16
}
17
 
18
dojo.experimental = function(/* String */ moduleName, /* String? */ extra){
19
	// summary: Marks code as experimental.
20
	// description:
21
	//		This can be used to mark a function, file, or module as
22
	//		experimental.  Experimental code is not ready to be used, and the
23
	//		APIs are subject to change without notice.  Experimental code may be
24
	//		completed deleted without going through the normal deprecation
25
	//		process.
26
	// moduleName:
27
	//		The name of a module, or the name of a module file or a specific
28
	//		function
29
	// extra:
30
	//		some additional message for the user
31
	// example:
32
	//	|	dojo.experimental("dojo.data.Result");
33
	// example:
34
	//	|	dojo.experimental("dojo.weather.toKelvin()", "PENDING approval from NOAA");
35
	var message = "EXPERIMENTAL: " + moduleName + " -- APIs subject to change without notice.";
36
	if(extra){ message += " " + extra; }
37
	console.debug(message);
38
}
39
 
40
// FIREBUG LITE
41
	// summary: Firebug Lite, the baby brother to Joe Hewitt's Firebug for Mozilla Firefox
42
	// description:
43
	//		Opens a console for logging, debugging, and error messages.
44
	//		Contains partial functionality to Firebug. See function list below.
45
	//	NOTE:
46
	//			Firebug is a Firefox extension created by Joe Hewitt (see license). You do not need Dojo to run Firebug.
47
	//			Firebug Lite is included in Dojo by permission from Joe Hewitt
48
	//			If you are new to Firebug, or used to the Dojo 0.4 dojo.debug, you can learn Firebug
49
	//				functionality by reading the function comments below or visiting http://www.getfirebug.com/docs.html
50
	//	NOTE:
51
	//		To test Firebug Lite in Firefox, set console = null;
52
	//
53
	// example:
54
	//		Supports inline objects in object inspector window (only simple trace of dom nodes, however)
55
	//		|	console.log("my object", {foo:"bar"})
56
	// example:
57
	//		Option for console to open in popup window
58
	//		|	var djConfig = {isDebug: true, popup:true };
59
	// example:
60
	//		Option for console height (ignored for popup)
61
	//		|	var djConfig = {isDebug: true, debugHeight:100 };
62
 
63
if(
64
	(
65
		(!("console" in window)) ||
66
		(!("firebug" in console))
67
	)&&
68
	(
69
		(djConfig["noFirebugLite"] !== true)
70
	)
71
){
72
(function(){
73
	// don't build a firebug frame in iframes
74
	try{
75
		if(window != window.parent){
76
			// but if we've got a parent logger, connect to it
77
			if(window.parent["console"]){
78
				window.console = window.parent.console;
79
			}
80
			return;
81
		}
82
	}catch(e){}
83
 
84
	window.console = {
85
		log: function(){
86
			// summary:
87
			//		Sends arguments to console.
88
			logFormatted(arguments, "");
89
		},
90
 
91
		debug: function(){
92
			// summary:
93
			//		Sends arguments to console. Missing finctionality to show script line of trace.
94
			logFormatted(arguments, "debug");
95
		},
96
 
97
		info: function(){
98
			// summary:
99
			//		Sends arguments to console, highlighted with (I) icon.
100
			logFormatted(arguments, "info");
101
		},
102
 
103
		warn: function(){
104
			// summary:
105
			//		Sends warning arguments to console, highlighted with (!) icon and blue style.
106
			logFormatted(arguments, "warning");
107
		},
108
 
109
		error: function(){
110
			// summary:
111
			//		Sends error arguments (object) to console, highlighted with (X) icon and yellow style
112
			//			NEW: error object now displays in object inspector
113
			logFormatted(arguments, "error");
114
		},
115
 
116
		assert: function(truth, message){
117
			// summary:
118
			//		Tests for true. Throws exception if false.
119
			if(!truth){
120
				var args = [];
121
				for(var i = 1; i < arguments.length; ++i){
122
					args.push(arguments[i]);
123
				}
124
 
125
				logFormatted(args.length ? args : ["Assertion Failure"], "error");
126
				throw message ? message : "Assertion Failure";
127
			}
128
		},
129
 
130
		dir: function(object){
131
			// summary:
132
			//		Traces object. Only partially implemented.
133
			var html = [];
134
 
135
			var pairs = [];
136
			for(var name in object){
137
				try{
138
					pairs.push([name, object[name]]);
139
				}catch(e){
140
					/* squelch */
141
				}
142
			}
143
 
144
			pairs.sort(function(a, b){
145
				return a[0] < b[0] ? -1 : 1;
146
			});
147
 
148
			html.push('<table>');
149
			for(var i = 0; i < pairs.length; ++i){
150
				var name = pairs[i][0], value = pairs[i][1];
151
 
152
				html.push('<tr>',
153
				'<td class="propertyNameCell"><span class="propertyName">',
154
					escapeHTML(name), '</span></td>', '<td><span class="propertyValue">');
155
				appendObject(value, html);
156
				html.push('</span></td></tr>');
157
			}
158
			html.push('</table>');
159
 
160
			logRow(html, "dir");
161
		},
162
 
163
		dirxml: function(node){
164
			// summary:
165
			//
166
			var html = [];
167
 
168
			appendNode(node, html);
169
			logRow(html, "dirxml");
170
		},
171
 
172
		group: function(){
173
			// summary:
174
			//		collects log messages into a group, starting with this call and ending with
175
			//			groupEnd(). Missing collapse functionality
176
			logRow(arguments, "group", pushGroup);
177
		},
178
 
179
		groupEnd: function(){
180
			// summary:
181
			//		Closes group. See above
182
			logRow(arguments, "", popGroup);
183
		},
184
 
185
		time: function(name){
186
			// summary:
187
			//		Starts timers assigned to name given in argument. Timer stops and displays on timeEnd(title);
188
			//	example:
189
			//	|	console.time("load");
190
			//	|	console.time("myFunction");
191
			//	|	console.timeEnd("load");
192
			//	|	console.timeEnd("myFunction");
193
			timeMap[name] = (new Date()).getTime();
194
		},
195
 
196
		timeEnd: function(name){
197
			// summary:
198
			//		See above.
199
			if(name in timeMap){
200
				var delta = (new Date()).getTime() - timeMap[name];
201
				logFormatted([name+ ":", delta+"ms"]);
202
				delete timeMap[name];
203
			}
204
		},
205
 
206
		count: function(){
207
			// summary:
208
			//		Not supported
209
			this.warn(["count() not supported."]);
210
		},
211
 
212
		trace: function(){
213
			// summary:
214
			//		Not supported
215
			this.warn(["trace() not supported."]);
216
		},
217
 
218
		profile: function(){
219
			// summary:
220
			//		Not supported
221
			this.warn(["profile() not supported."]);
222
		},
223
 
224
		profileEnd: function(){ },
225
 
226
		clear: function(){
227
			// summary:
228
			//		Clears message console. Do not call this directly
229
			consoleBody.innerHTML = "";
230
		},
231
 
232
		open: function(){
233
			// summary:
234
			//		Opens message console. Do not call this directly
235
			toggleConsole(true);
236
		},
237
 
238
		close: function(){
239
			// summary:
240
			//		Closes message console. Do not call this directly
241
			if(frameVisible){
242
				toggleConsole();
243
			}
244
		},
245
		closeObjectInspector:function(){
246
			// summary:
247
			//		Closes object inspector and opens message console. Do not call this directly
248
			consoleObjectInspector.innerHTML = "";
249
			consoleObjectInspector.style.display = "none";
250
			consoleBody.style.display = "block";
251
		}
252
	};
253
 
254
	// ***************************************************************************
255
 
256
	// using global objects so they can be accessed
257
	// most of the objects in this script are run anonomously
258
	var _firebugDoc = document;
259
	var _firebugWin = window;
260
	var __consoleAnchorId__ = 0;
261
 
262
	var consoleFrame = null;
263
	var consoleBody = null;
264
	var commandLine = null;
265
 
266
	var frameVisible = false;
267
	var messageQueue = [];
268
	var groupStack = [];
269
	var timeMap = {};
270
 
271
	var clPrefix = ">>> ";
272
 
273
	// ***************************************************************************
274
 
275
	function toggleConsole(forceOpen){
276
		frameVisible = forceOpen || !frameVisible;
277
		if(consoleFrame){
278
			consoleFrame.style.display = frameVisible ? "block" : "none";
279
		}
280
	}
281
 
282
	function focusCommandLine(){
283
		toggleConsole(true);
284
		if(commandLine){
285
			commandLine.focus();
286
		}
287
	}
288
 
289
	openWin = function(){
290
		var win = window.open("","_firebug","status=0,menubar=0,resizable=1,width=640,height=480,scrollbars=1,addressbar=0");
291
		var newDoc=win.document;
292
		HTMLstring='<html><head><title>Firebug Lite</title></head>\n';
293
		HTMLstring+='<body bgColor="#CCCCCC">\n';
294
		//Testing access to dojo from the popup window
295
		/*HTMLstring+='<button onclick="(function(){ console.log(dojo.version.toString()); })()">Test Parent Dojo</button>\n';*/
296
		HTMLstring+='<div id="fb"></div>';
297
		HTMLstring+='</body></html>';
298
 
299
 
300
		newDoc.write(HTMLstring);
301
		newDoc.close();
302
		return win;
303
 
304
	}
305
 
306
	function createFrame(){
307
		if(consoleFrame){
308
			return;
309
		}
310
 
311
		if(djConfig.popup){
312
			_firebugWin = openWin();
313
			_firebugDoc = _firebugWin.document;
314
			djConfig.debugContainerId = 'fb';
315
			var containerHeight = "100%";
316
 
317
			// connecting popup
318
			_firebugWin.console = window.console;
319
			_firebugWin.dojo = window.dojo;
320
 
321
		}else{
322
			_firebugDoc = document;
323
			var containerHeight = (djConfig.debugHeight) ? djConfig.debugHeight + "px" :"300px";
324
		}
325
 
326
		var styleElement = _firebugDoc.createElement("link");
327
		styleElement.href = dojo.moduleUrl("dojo._firebug", "firebug.css");
328
		styleElement.rel = "stylesheet";
329
		styleElement.type = "text/css";
330
		var styleParent = _firebugDoc.getElementsByTagName("head");
331
		if(styleParent){
332
			styleParent = styleParent[0];
333
		}
334
		if(!styleParent){
335
			styleParent = _firebugDoc.getElementsByTagName("html")[0];
336
		}
337
		if(dojo.isIE){
338
			window.setTimeout(function(){ styleParent.appendChild(styleElement); }, 0);
339
		}else{
340
			styleParent.appendChild(styleElement);
341
		}
342
 
343
		if(typeof djConfig != "undefined" && djConfig["debugContainerId"]){
344
			consoleFrame = _firebugDoc.getElementById(djConfig.debugContainerId);
345
		}
346
		if(!consoleFrame){
347
			consoleFrame = _firebugDoc.createElement("div");
348
			_firebugDoc.body.appendChild(consoleFrame);
349
		}
350
		consoleFrame.className += " firebug";
351
		consoleFrame.style.height = containerHeight;
352
		consoleFrame.style.display = (frameVisible ? "block" : "none");
353
 
354
		var closeStr = (djConfig.popup) ? "" : '    <a href="#" onclick="console.close(); return false;">Close</a>';
355
		consoleFrame.innerHTML =
356
			  '<div id="firebugToolbar">'
357
			+ '  <a href="#" onclick="console.clear(); return false;">Clear</a>'
358
			+ '  <span class="firebugToolbarRight">'
359
			+ closeStr
360
			+ '  </span>'
361
			+ '</div>'
362
			+ '<input type="text" id="firebugCommandLine">'
363
			+ '<div id="firebugLog"></div>'
364
			+ '<div id="objectLog" style="display:none;"></div>';
365
 
366
 
367
		var toolbar = _firebugDoc.getElementById("firebugToolbar");
368
		toolbar.onmousedown = onSplitterMouseDown;
369
 
370
		commandLine = _firebugDoc.getElementById("firebugCommandLine");
371
		addEvent(commandLine, "keydown", onCommandLineKeyDown);
372
 
373
		addEvent(_firebugDoc, dojo.isIE || dojo.isSafari ? "keydown" : "keypress", onKeyDown);
374
 
375
		consoleBody = _firebugDoc.getElementById("firebugLog");
376
		consoleObjectInspector = _firebugDoc.getElementById("objectLog");
377
 
378
		layout();
379
		flush();
380
	}
381
 
382
	dojo.addOnLoad(createFrame);
383
 
384
	function evalCommandLine(){
385
		var text = commandLine.value;
386
		commandLine.value = "";
387
 
388
		logRow([clPrefix, text], "command");
389
 
390
		var value;
391
		try{
392
			value = eval(text);
393
		}catch(e){
394
			console.debug(e);
395
			/* squelch */
396
		}
397
 
398
		console.log(value);
399
	}
400
 
401
	function layout(){
402
		var toolbar = consoleBody.ownerDocument.getElementById("firebugToolbar");
403
		var height = consoleFrame.offsetHeight - (toolbar.offsetHeight + commandLine.offsetHeight);
404
		consoleBody.style.top = toolbar.offsetHeight + "px";
405
		consoleBody.style.height = height + "px";
406
 
407
		commandLine.style.top = (consoleFrame.offsetHeight - commandLine.offsetHeight) + "px";
408
	}
409
 
410
	function logRow(message, className, handler){
411
		if(consoleBody){
412
			writeMessage(message, className, handler);
413
		}else{
414
			messageQueue.push([message, className, handler]);
415
		}
416
	}
417
 
418
	function flush(){
419
		var queue = messageQueue;
420
		messageQueue = [];
421
 
422
		for(var i = 0; i < queue.length; ++i){
423
			writeMessage(queue[i][0], queue[i][1], queue[i][2]);
424
		}
425
	}
426
 
427
	function writeMessage(message, className, handler){
428
		var isScrolledToBottom =
429
			consoleBody.scrollTop + consoleBody.offsetHeight >= consoleBody.scrollHeight;
430
 
431
		handler = handler||writeRow;
432
 
433
		handler(message, className);
434
 
435
		if(isScrolledToBottom){
436
			consoleBody.scrollTop = consoleBody.scrollHeight - consoleBody.offsetHeight;
437
		}
438
	}
439
 
440
	function appendRow(row){
441
		var container = groupStack.length ? groupStack[groupStack.length-1] : consoleBody;
442
		container.appendChild(row);
443
	}
444
 
445
	function writeRow(message, className){
446
		var row = consoleBody.ownerDocument.createElement("div");
447
		row.className = "logRow" + (className ? " logRow-"+className : "");
448
		row.innerHTML = message.join("");
449
		appendRow(row);
450
	}
451
 
452
	function pushGroup(message, className){
453
		logFormatted(message, className);
454
 
455
		var groupRow = consoleBody.ownerDocument.createElement("div");
456
		groupRow.className = "logGroup";
457
		var groupRowBox = consoleBody.ownerDocument.createElement("div");
458
		groupRowBox.className = "logGroupBox";
459
		groupRow.appendChild(groupRowBox);
460
		appendRow(groupRowBox);
461
		groupStack.push(groupRowBox);
462
	}
463
 
464
	function popGroup(){
465
		groupStack.pop();
466
	}
467
 
468
	// ***************************************************************************
469
 
470
	function logFormatted(objects, className){
471
		var html = [];
472
 
473
		var format = objects[0];
474
		var objIndex = 0;
475
 
476
		if(typeof(format) != "string"){
477
			format = "";
478
			objIndex = -1;
479
		}
480
 
481
		var parts = parseFormat(format);
482
 
483
		for(var i = 0; i < parts.length; ++i){
484
			var part = parts[i];
485
			if(part && typeof(part) == "object"){
486
				var object = objects[++objIndex];
487
				part.appender(object, html);
488
			}else{
489
				appendText(part, html);
490
			}
491
		}
492
 
493
 
494
		var ids = [];
495
		var obs = [];
496
		for(var i = objIndex+1; i < objects.length; ++i){
497
			appendText(" ", html);
498
 
499
			var object = objects[i];
500
			if(!object){ continue; }
501
			if(typeof(object) == "string"){
502
				appendText(object, html);
503
 
504
			}else if(object.nodeType == 1){
505
				// simple tracing of dom nodes
506
				appendText("< "+object.tagName+" id=\""+ object.id+"\" />", html);
507
 
508
			}else{
509
				// Create link for object inspector
510
				// need to create an ID for this link, since it is currently text
511
				var id = "_a" + __consoleAnchorId__++;
512
				ids.push(id);
513
				// need to save the object, so the arrays line up
514
				obs.push(object)
515
				var str = '<a id="'+id+'" href="javascript:void(0);">'+getObjectAbbr(object)+'</a>';
516
 
517
				appendLink( str , html);
518
			}
519
		}
520
 
521
		logRow(html, className);
522
 
523
		// Now that the row is inserted in the DOM, loop through all of the links that were just created
524
		for(var i=0; i<ids.length; i++){
525
			var btn = _firebugDoc.getElementById(ids[i]);
526
			if(!btn){ continue; }
527
 
528
			// store the object in the dom btn for reference later
529
			// avoid parsing these objects unless necessary
530
			btn.obj = obs[i];
531
 
532
			dojo.connect(btn, "onclick", function(){
533
				// hide rows
534
				consoleBody.style.display = "none";
535
				consoleObjectInspector.style.display = "block";
536
				// create a back button
537
				var bkBtn = '<a href="javascript:console.closeObjectInspector();">&nbsp;<<&nbsp;Back</a>';
538
				consoleObjectInspector.innerHTML = bkBtn + "<pre>" + printObject( this.obj ) + "</pre>";
539
 
540
			})
541
 
542
		}
543
	}
544
 
545
	function parseFormat(format){
546
		var parts = [];
547
 
548
		var reg = /((^%|[^\\]%)(\d+)?(\.)([a-zA-Z]))|((^%|[^\\]%)([a-zA-Z]))/;
549
		var appenderMap = {s: appendText, d: appendInteger, i: appendInteger, f: appendFloat};
550
 
551
		for(var m = reg.exec(format); m; m = reg.exec(format)){
552
			var type = m[8] ? m[8] : m[5];
553
			var appender = type in appenderMap ? appenderMap[type] : appendObject;
554
			var precision = m[3] ? parseInt(m[3]) : (m[4] == "." ? -1 : 0);
555
 
556
			parts.push(format.substr(0, m[0][0] == "%" ? m.index : m.index+1));
557
			parts.push({appender: appender, precision: precision});
558
 
559
			format = format.substr(m.index+m[0].length);
560
		}
561
 
562
		parts.push(format);
563
 
564
		return parts;
565
	}
566
 
567
	function escapeHTML(value){
568
		function replaceChars(ch){
569
			switch(ch){
570
				case "<":
571
					return "&lt;";
572
				case ">":
573
					return "&gt;";
574
				case "&":
575
					return "&amp;";
576
				case "'":
577
					return "&#39;";
578
				case '"':
579
					return "&quot;";
580
			}
581
			return "?";
582
		};
583
		return String(value).replace(/[<>&"']/g, replaceChars);
584
	}
585
 
586
	function objectToString(object){
587
		try{
588
			return object+"";
589
		}catch(e){
590
			return null;
591
		}
592
	}
593
 
594
	// ***************************************************************************
595
	function appendLink(object, html){
596
		// needed for object links - no HTML escaping
597
		html.push( objectToString(object) );
598
	}
599
 
600
	function appendText(object, html){
601
		html.push(escapeHTML(objectToString(object)));
602
	}
603
 
604
	function appendNull(object, html){
605
		html.push('<span class="objectBox-null">', escapeHTML(objectToString(object)), '</span>');
606
	}
607
 
608
	function appendString(object, html){
609
		html.push('<span class="objectBox-string">&quot;', escapeHTML(objectToString(object)),
610
			'&quot;</span>');
611
	}
612
 
613
	function appendInteger(object, html){
614
		html.push('<span class="objectBox-number">', escapeHTML(objectToString(object)), '</span>');
615
	}
616
 
617
	function appendFloat(object, html){
618
		html.push('<span class="objectBox-number">', escapeHTML(objectToString(object)), '</span>');
619
	}
620
 
621
	function appendFunction(object, html){
622
		var reName = /function ?(.*?)\(/;
623
		var m = reName.exec(objectToString(object));
624
		var name = m ? m[1] : "function";
625
		html.push('<span class="objectBox-function">', escapeHTML(name), '()</span>');
626
	}
627
 
628
	function appendObject(object, html){
629
		try{
630
			if(object == undefined){
631
				appendNull("undefined", html);
632
			}else if(object == null){
633
				appendNull("null", html);
634
			}else if(typeof object == "string"){
635
				appendString(object, html);
636
			}else if(typeof object == "number"){
637
				appendInteger(object, html);
638
			}else if(typeof object == "function"){
639
				appendFunction(object, html);
640
			}else if(object.nodeType == 1){
641
				appendSelector(object, html);
642
			}else if(typeof object == "object"){
643
				appendObjectFormatted(object, html);
644
			}else{
645
				appendText(object, html);
646
			}
647
		}catch(e){
648
			/* squelch */
649
		}
650
	}
651
 
652
	function appendObjectFormatted(object, html){
653
		var text = objectToString(object);
654
		var reObject = /\[object (.*?)\]/;
655
 
656
		var m = reObject.exec(text);
657
		html.push('<span class="objectBox-object">', m ? m[1] : text, '</span>')
658
	}
659
 
660
	function appendSelector(object, html){
661
		html.push('<span class="objectBox-selector">');
662
 
663
		html.push('<span class="selectorTag">', escapeHTML(object.nodeName.toLowerCase()), '</span>');
664
		if(object.id){
665
			html.push('<span class="selectorId">#', escapeHTML(object.id), '</span>');
666
		}
667
		if(object.className){
668
			html.push('<span class="selectorClass">.', escapeHTML(object.className), '</span>');
669
		}
670
 
671
		html.push('</span>');
672
	}
673
 
674
	function appendNode(node, html){
675
		if(node.nodeType == 1){
676
			html.push(
677
				'<div class="objectBox-element">',
678
					'&lt;<span class="nodeTag">', node.nodeName.toLowerCase(), '</span>');
679
 
680
			for(var i = 0; i < node.attributes.length; ++i){
681
				var attr = node.attributes[i];
682
				if(!attr.specified){ continue; }
683
 
684
				html.push('&nbsp;<span class="nodeName">', attr.nodeName.toLowerCase(),
685
					'</span>=&quot;<span class="nodeValue">', escapeHTML(attr.nodeValue),
686
					'</span>&quot;')
687
			}
688
 
689
			if(node.firstChild){
690
				html.push('&gt;</div><div class="nodeChildren">');
691
 
692
				for(var child = node.firstChild; child; child = child.nextSibling){
693
					appendNode(child, html);
694
				}
695
 
696
				html.push('</div><div class="objectBox-element">&lt;/<span class="nodeTag">',
697
					node.nodeName.toLowerCase(), '&gt;</span></div>');
698
			}else{
699
				html.push('/&gt;</div>');
700
			}
701
		}else if (node.nodeType == 3){
702
			html.push('<div class="nodeText">', escapeHTML(node.nodeValue),
703
				'</div>');
704
		}
705
	}
706
 
707
	// ***************************************************************************
708
 
709
	function addEvent(object, name, handler){
710
		if(document.all){
711
			object.attachEvent("on"+name, handler);
712
		}else{
713
			object.addEventListener(name, handler, false);
714
		}
715
	}
716
 
717
	function removeEvent(object, name, handler){
718
		if(document.all){
719
			object.detachEvent("on"+name, handler);
720
		}else{
721
			object.removeEventListener(name, handler, false);
722
		}
723
	}
724
 
725
	function cancelEvent(event){
726
		if(document.all){
727
			event.cancelBubble = true;
728
		}else{
729
			event.stopPropagation();
730
		}
731
	}
732
 
733
	function onError(msg, href, lineNo){
734
		var html = [];
735
 
736
		var lastSlash = href.lastIndexOf("/");
737
		var fileName = lastSlash == -1 ? href : href.substr(lastSlash+1);
738
 
739
		html.push(
740
			'<span class="errorMessage">', msg, '</span>',
741
			'<div class="objectBox-sourceLink">', fileName, ' (line ', lineNo, ')</div>'
742
		);
743
 
744
		logRow(html, "error");
745
	};
746
 
747
 
748
	//After converting to div instead of iframe, now getting two keydowns right away in IE 6.
749
	//Make sure there is a little bit of delay.
750
	var onKeyDownTime = (new Date()).getTime();
751
 
752
	function onKeyDown(event){
753
		var timestamp = (new Date()).getTime();
754
		if(timestamp > onKeyDownTime + 200){
755
			var event = dojo.fixEvent(event);
756
			var keys = dojo.keys;
757
			var ekc = event.keyCode;
758
			onKeyDownTime = timestamp;
759
			if(ekc == keys.F12){
760
				toggleConsole();
761
			}else if(
762
				(ekc == keys.NUMPAD_ENTER || ekc == 76) &&
763
				event.shiftKey &&
764
				(event.metaKey || event.ctrlKey)
765
			){
766
				focusCommandLine();
767
			}else{
768
				return;
769
			}
770
			cancelEvent(event);
771
		}
772
	}
773
 
774
 
775
	function onSplitterMouseDown(event){
776
		if(dojo.isSafari || dojo.isOpera){
777
			return;
778
		}
779
 
780
		addEvent(document, "mousemove", onSplitterMouseMove);
781
		addEvent(document, "mouseup", onSplitterMouseUp);
782
 
783
		for(var i = 0; i < frames.length; ++i){
784
			addEvent(frames[i].document, "mousemove", onSplitterMouseMove);
785
			addEvent(frames[i].document, "mouseup", onSplitterMouseUp);
786
		}
787
	}
788
 
789
	function onSplitterMouseMove(event){
790
		var win = document.all
791
			? event.srcElement.ownerDocument.parentWindow
792
			: event.target.ownerDocument.defaultView;
793
 
794
		var clientY = event.clientY;
795
		if(win != win.parent){
796
			clientY += win.frameElement ? win.frameElement.offsetTop : 0;
797
		}
798
 
799
		var height = consoleFrame.offsetTop + consoleFrame.clientHeight;
800
		var y = height - clientY;
801
 
802
		consoleFrame.style.height = y + "px";
803
		layout();
804
	}
805
 
806
	function onSplitterMouseUp(event){
807
		removeEvent(document, "mousemove", onSplitterMouseMove);
808
		removeEvent(document, "mouseup", onSplitterMouseUp);
809
 
810
		for(var i = 0; i < frames.length; ++i){
811
			removeEvent(frames[i].document, "mousemove", onSplitterMouseMove);
812
			removeEvent(frames[i].document, "mouseup", onSplitterMouseUp);
813
		}
814
	}
815
 
816
	function onCommandLineKeyDown(event){
817
		if(event.keyCode == 13){
818
			evalCommandLine();
819
		}else if(event.keyCode == 27){
820
			commandLine.value = "";
821
		}
822
	}
823
	//***************************************************************************************************
824
	// Print Object Helpers
825
	getAtts = function(o){
826
		//Get amount of items in an object
827
		if(dojo.isArray(o)) {
828
			return "[array with " + o.length + " slots]";
829
		}else{
830
			var i = 0;
831
			for(var nm in o){
832
				i++;
833
			}
834
			return "{object with " + i + " items}";
835
		}
836
	}
837
 
838
	printObject = function(o, i, txt){
839
 
840
		// Recursively trace object, indenting to represent depth for display in object inspector
841
		// TODO: counter to prevent overly complex or looped objects (will probably help with dom nodes)
842
		var br = "\n"; // using a <pre>... otherwise we'd need a <br />
843
		var ind = "  ";
844
		txt = (txt) ? txt : "";
845
		i = (i) ? i : ind;
846
		for(var nm in o){
847
			if(typeof(o[nm]) == "object"){
848
				txt += i+nm +" -> " + getAtts(o[nm]) + br;
849
				txt += printObject(o[nm], i+ind);
850
			}else{
851
				txt += i+nm +" : "+o[nm] + br;
852
			}
853
		}
854
		return txt;
855
	}
856
 
857
 
858
	getObjectAbbr = function(obj){
859
		// Gets an abbreviation of an object for display in log
860
		// X items in object, including id
861
		// X items in an array
862
		// TODO: Firebug Sr. actually goes by char count
863
		var isError = (obj instanceof Error);
864
		var nm = obj.id || obj.name || obj.ObjectID || obj.widgetId;
865
		if(!isError && nm){ return "{"+nm+"}";	}
866
 
867
		var obCnt = 2;
868
		var arCnt = 4;
869
		var cnt = 0;
870
 
871
		if(isError){
872
			nm = "[ Error: "+(obj["message"]||obj["description"]||obj)+" ]";
873
		}else if(dojo.isArray(obj)){
874
			nm ="[";
875
			for(var i=0;i<obj.length;i++){
876
				nm+=obj[i]+","
877
				if(i>arCnt){
878
					nm+=" ... ("+obj.length+" items)";
879
					break;
880
				}
881
			}
882
			nm+="]";
883
		}else if((!dojo.isObject(obj))||dojo.isString(obj)){
884
			nm = obj+"";
885
		}else{
886
			nm = "{";
887
			for(var i in obj){
888
				cnt++
889
				if(cnt > obCnt) break;
890
				nm += i+"="+obj[i]+"  ";
891
			}
892
			nm+="}"
893
		}
894
 
895
		return nm;
896
	}
897
 
898
	//*************************************************************************************
899
 
900
	window.onerror = onError;
901
	addEvent(document, dojo.isIE || dojo.isSafari ? "keydown" : "keypress", onKeyDown);
902
 
903
	if(	(document.documentElement.getAttribute("debug") == "true")||
904
		(djConfig.isDebug)
905
	){
906
		toggleConsole(true);
907
	}
908
})();
909
}
910
 
911
}