PageSourceSearch

https://www.zqx.gov.cn/_dwr/util.js

js zqx.gov.cn collected 2026-10-02 17:04:43 UTC 46,648 bytes, 1,487 lines download raw bytes

1/*
2 * Copyright 2005 Joe Walker
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 *     http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17/**
18 * Declare an object to which we can add real functions.
19 */
20if (dwr == null) var dwr = {};
21if (dwr.util == null) dwr.util = {};
22if (DWRUtil == null) var DWRUtil = dwr.util;
23
24/** @private The flag we use to decide if we should escape html */
25dwr.util._escapeHtml = true;
26
27/**
28 * Set the global escapeHtml flag
29 */
30dwr.util.setEscapeHtml = function(escapeHtml) {
31  dwr.util._escapeHtml = escapeHtml;
32};
33
34/** @private Work out from an options list and global settings if we should be esccaping */
35dwr.util._shouldEscapeHtml = function(options) {
36  if (options && options.escapeHtml != null) {
37    return options.escapeHtml;
38  }
39  return dwr.util._escapeHtml;
40};
41
42/**
43 * Return a string with &, < and > replaced with their entities
44 * @see TODO
45 */
46dwr.util.escapeHtml = function(original) {
47  return original.replace(/&/g,'&amp;').replace(/</g,'&lt;').replace(/>/g,'&gt;');
48};
49
50/**
51 * Replace common XML entities with characters (see dwr.util.escapeHtml())
52 * @see TODO
53 */
54dwr.util.unescapeHtml = function(original) {
55  return original.replace(/&amp;/g,'&').replace(/&lt;/g,'<').replace(/&gt;/g,'>');
56};
57
58/**
59 * Replace characters dangerous for XSS reasons with visually similar characters
60 * @see TODO
61 */
62dwr.util.replaceXmlCharacters = function(original) {
63  original = original.replace("&", "+");
64  original = original.replace("<", "\u2039");
65  original = original.replace(">", "\u203A");
66  original = original.replace("\'", "\u2018");
67  original = original.replace("\"", "\u201C");
68  return original;
69};
70
71/**
72 * Return true iff the input string contains any XSS dangerous characters
73 * @see TODO
74 */
75dwr.util.containsXssRiskyCharacters = function(original) {
76  return (original.indexOf('&') != -1
77    || original.indexOf('<') != -1
78    || original.indexOf('>') != -1
79    || original.indexOf('\'') != -1
80    || original.indexOf('\"') != -1);
81};
82
83/**
84 * Enables you to react to return being pressed in an input
85 * @see http://getahead.org/dwr/browser/util/selectrange
86 */
87dwr.util.onReturn = function(event, action) {
88  if (!event) event = window.event;
89  if (event && event.keyCode && event.keyCode == 13) action();
90};
91
92/**
93 * Select a specific range in a text box. Useful for 'google suggest' type functions.
94 * @see http://getahead.org/dwr/browser/util/selectrange
95 */
96dwr.util.selectRange = function(ele, start, end) {
97  ele = dwr.util._getElementById(ele, "selectRange()");
98  if (ele == null) return;
99  if (ele.setSelectionRange) {
100    ele.setSelectionRange(start, end);
101  }
102  else if (ele.createTextRange) {
103    var range = ele.createTextRange();
104    range.moveStart("character", start);
105    range.moveEnd("character", end - ele.value.length);
106    range.select();
107  }
108  ele.focus();
109};
110
111/**
112 * Find the element in the current HTML document with the given id or ids
113 * @see http://getahead.org/dwr/browser/util/$
114 */
115if (document.getElementById) {
116  dwr.util.byId = function() {
117    var elements = new Array();
118    for (var i = 0; i < arguments.length; i++) {
119      var element = arguments[i];
120      if (typeof element == 'string') {
121        element = document.getElementById(element);
122      }
123      if (arguments.length == 1) {
124        return element;
125      }
126      elements.push(element);
127    }
128    return elements;
129  };
130}
131else if (document.all) {
132  dwr.util.byId = function() {
133    var elements = new Array();
134    for (var i = 0; i < arguments.length; i++) {
135      var element = arguments[i];
136      if (typeof element == 'string') {
137        element = document.all[element];
138      }
139      if (arguments.length == 1) {
140        return element;
141      }
142      elements.push(element);
143    }
144    return elements;
145  };
146}
147
148/**
149 * Alias $ to dwr.util.byId
150 * @see http://getahead.org/dwr/browser/util/$
151 */
152if (window['$'] == null) {
153  window['$'] = dwr.util.byId;
154}
155
156/**
157 * This function pretty-prints simple data or whole object graphs, f ex as an aid in debugging.
158 * @see http://getahead.org/dwr/browser/util/todescriptivestring
159 */
160dwr.util.toDescriptiveString = function(data, showLevels, options) {
161  if (showLevels === undefined) showLevels = 1;
162  var opt = {};
163  if (dwr.util._isObject(options)) opt = options;
164  var defaultoptions = {
165    escapeHtml:false,
166    baseIndent: "",
167    childIndent: "\u00A0\u00A0",
168    lineTerminator: "\n",
169    oneLineMaxItems: 5,
170    shortStringMaxLength: 13,
171    propertyNameMaxLength: 30 
172  };
173  for (var p in defaultoptions) {
174    if (!(p in opt)) {
175      opt[p] = defaultoptions[p];
176    }
177  }
178
179  var skipDomProperties = {
180    document:true, ownerDocument:true,
181    all:true,
182    parentElement:true, parentNode:true, offsetParent:true,
183    children:true, firstChild:true, lastChild:true,
184    previousSibling:true, nextSibling:true,
185    innerHTML:true, outerHTML:true,
186    innerText:true, outerText:true, textContent:true,
187    attributes:true,
188    style:true, currentStyle:true, runtimeStyle:true,
189    parentTextEdit:true
190  };
191  
192  function recursive(data, showLevels, indentDepth, options) {
193    var reply = "";
194    try {
195      // string
196      if (typeof data == "string") {
197        var str = data;
198        if (showLevels == 0 && str.length > options.shortStringMaxLength)
199          str = str.substring(0, options.shortStringMaxLength-3) + "...";
200        if (options.escapeHtml) {
201          // Do the escape separately for every line as escapeHtml() on some 
202          // browsers (IE) will strip line breaks and we want to preserve them
203          var lines = str.split("\n");
204          for (var i = 0; i < lines.length; i++) lines[i] = dwr.util.escapeHtml(lines[i]);
205          str = lines.join("\n");
206        }
207        if (showLevels == 0) { // Short format
208          str = str.replace(/\n|\r|\t/g, function(ch) {
209            switch (ch) {
210              case "\n": return "\\n";
211              case "\r": return "";
212              case "\t": return "\\t";
213            }
214          });
215        }
216        else { // Long format
217          str = str.replace(/\n|\r|\t/g, function(ch) {
218            switch (ch) {
219              case "\n": return options.lineTerminator + indent(indentDepth+1, options);
220              case "\r": return "";
221              case "\t": return "\\t";
222            }
223          });
224        }
225        reply = '"' + str + '"';
226      }
227      
228      // function
229      else if (typeof data == "function") {
230        reply = "function";
231      }
232    
233      // Array
234      else if (dwr.util._isArray(data)) {
235        if (showLevels == 0) { // Short format (don't show items)
236          if (data.length > 0)
237            reply = "[...]";
238          else
239            reply = "[]";
240        }
241        else { // Long format (show items)
242          var strarr = [];
243          strarr.push("[");
244          var count = 0;
245          for (var i = 0; i < data.length; i++) {
246            if (! (i in data)) continue;
247            var itemvalue = data[i];
248            if (count > 0) strarr.push(", ");
249            if (showLevels == 1) { // One-line format
250              if (count == options.oneLineMaxItems) {
251                strarr.push("...");
252                break;
253              }
254            }
255            else { // Multi-line format
256              strarr.push(options.lineTerminator + indent(indentDepth+1, options));
257            }
258            if (i != count) {
259              strarr.push(i);
260              strarr.push(":");
261            }
262            strarr.push(recursive(itemvalue, showLevels-1, indentDepth+1, options));
263            count++;
264          }
265          if (showLevels > 1) strarr.push(options.lineTerminator + indent(indentDepth, options));
266          strarr.push("]");
267          reply = strarr.join("");
268        }
269      }
270      
271      // Objects except Date
272      else if (dwr.util._isObject(data) && !dwr.util._isDate(data)) {
273        if (showLevels == 0) { // Short format (don't show properties)
274          reply = dwr.util._detailedTypeOf(data);
275        }
276        else { // Long format (show properties)
277          var strarr = [];
278          if (dwr.util._detailedTypeOf(data) != "Object") {
279            strarr.push(dwr.util._detailedTypeOf(data));
280            if (typeof data.valueOf() != "object") {
281              strarr.push(":");
282              strarr.push(recursive(data.valueOf(), 1, indentDepth, options));
283            }
284            strarr.push(" ");
285          }
286          strarr.push("{");
287          var isDomObject = dwr.util._isHTMLElement(data); 
288          var count = 0;
289          for (var prop in data) {
290            var propvalue = data[prop];
291            if (isDomObject) {
292              if (!propvalue) continue;
293              if (typeof propvalue == "function") continue;
294              if (skipDomProperties[prop]) continue;
295              if (prop.toUpperCase() == prop) continue;
296            }
297            if (count > 0) strarr.push(", ");
298            if (showLevels == 1) { // One-line format
299              if (count == options.oneLineMaxItems) {
300                strarr.push("...");
301                break;
302              }
303            }
304            else { // Multi-line format
305              strarr.push(options.lineTerminator + indent(indentDepth+1, options));
306            }
307            strarr.push(prop.length > options.propertyNameMaxLength ? prop.substring(0, options.propertyNameMaxLength-3) + "..." : prop);
308            strarr.push(":");
309            strarr.push(recursive(propvalue, showLevels-1, indentDepth+1, options));
310            count++;
311          }
312          if (showLevels > 1 && count > 0) strarr.push(options.lineTerminator + indent(indentDepth, options));
313          strarr.push("}");
314          reply = strarr.join("");
315        }
316      }
317  
318      // undefined, null, number, boolean, Date
319      else {
320        reply = "" + data;
321      }
322  
323      return reply;
324    }
325    catch(err) {
326      return (err.message ? err.message : ""+err);
327    }
328  }
329
330  function indent(count, options) {
331    var strarr = [];
332    strarr.push(options.baseIndent);
333    for (var i=0; i<count; i++) {
334      strarr.push(options.childIndent);
335    }
336    return strarr.join("");
337  };
338  
339  return recursive(data, showLevels, 0, opt);
340};
341
342/**
343 * Setup a GMail style loading message.
344 * @see http://getahead.org/dwr/browser/util/useloadingmessage
345 */
346dwr.util.useLoadingMessage = function(message) {
347  var loadingMessage;
348  if (message) loadingMessage = message;
349  else loadingMessage = "Loading";
350  dwr.engine.setPreHook(function() {
351    var disabledZone = dwr.util.byId('disabledZone');
352    if (!disabledZone) {
353      disabledZone = document.createElement('div');
354      disabledZone.setAttribute('id', 'disabledZone');
355      disabledZone.style.position = "absolute";
356      disabledZone.style.zIndex = "1000";
357      disabledZone.style.left = "0px";
358      disabledZone.style.top = "0px";
359      disabledZone.style.width = "100%";
360      disabledZone.style.height = "100%";
361      document.body.appendChild(disabledZone);
362      var messageZone = document.createElement('div');
363      messageZone.setAttribute('id', 'messageZone');
364      messageZone.style.position = "absolute";
365      messageZone.style.top = "0px";
366      messageZone.style.right = "0px";
367      messageZone.style.background = "red";
368      messageZone.style.color = "white";
369      messageZone.style.fontFamily = "Arial,Helvetica,sans-serif";
370      messageZone.style.padding = "4px";
371      disabledZone.appendChild(messageZone);
372      var text = document.createTextNode(loadingMessage);
373      messageZone.appendChild(text);
374      dwr.util._disabledZoneUseCount = 1;
375    }
376    else {
377      dwr.util.byId('messageZone').innerHTML = loadingMessage;
378      disabledZone.style.visibility = 'visible';
379      dwr.util._disabledZoneUseCount++;
380    }
381  });
382  dwr.engine.setPostHook(function() {
383    dwr.util._disabledZoneUseCount--;
384    if (dwr.util._disabledZoneUseCount == 0) {
385      dwr.util.byId('disabledZone').style.visibility = 'hidden';
386    }
387  });
388};
389
390/**
391 * Set a global highlight handler
392 */
393dwr.util.setHighlightHandler = function(handler) {
394  dwr.util._highlightHandler = handler;
395};
396
397/**
398 * An example highlight handler
399 */
400dwr.util.yellowFadeHighlightHandler = function(ele) {
401  dwr.util._yellowFadeProcess(ele, 0);
402};
403dwr.util._yellowFadeSteps = [ "d0", "b0", "a0", "90", "98", "a0", "a8", "b0", "b8", "c0", "c8", "d0", "d8", "e0", "e8", "f0", "f8" ];
404dwr.util._yellowFadeProcess = function(ele, colorIndex) {
405  ele = dwr.util.byId(ele);
406  if (colorIndex < dwr.util._yellowFadeSteps.length) {
407    ele.style.backgroundColor = "#ffff" + dwr.util._yellowFadeSteps[colorIndex];
408    setTimeout("dwr.util._yellowFadeProcess('" + ele.id + "'," + (colorIndex + 1) + ")", 200);
409  }
410  else {
411    ele.style.backgroundColor = "transparent";
412  }
413};
414
415/**
416 * An example highlight handler
417 */
418dwr.util.borderFadeHighlightHandler = function(ele) {
419  ele.style.borderWidth = "2px";
420  ele.style.borderStyle = "solid";
421  dwr.util._borderFadeProcess(ele, 0);
422};
423dwr.util._borderFadeSteps = [ "d0", "b0", "a0", "90", "98", "a0", "a8", "b0", "b8", "c0", "c8", "d0", "d8", "e0", "e8", "f0", "f8" ];
424dwr.util._borderFadeProcess = function(ele, colorIndex) {
425  ele = dwr.util.byId(ele);
426  if (colorIndex < dwr.util._borderFadeSteps.length) {
427    ele.style.borderColor = "#ff" + dwr.util._borderFadeSteps[colorIndex] + dwr.util._borderFadeSteps[colorIndex];
428    setTimeout("dwr.util._borderFadeProcess('" + ele.id + "'," + (colorIndex + 1) + ")", 200);
429  }
430  else {
431    ele.style.backgroundColor = "transparent";
432  }
433};
434
435/**
436 * A focus highlight handler
437 */
438dwr.util.focusHighlightHandler = function(ele) {
439  try {
440    ele.focus();
441  }
442  catch (ex) { /* ignore */ }
443};
444
445/** @private the current global highlight style */
446dwr.util._highlightHandler = null;
447
448/**
449 * Highlight that an element has changed
450 */
451dwr.util.highlight = function(ele, options) {
452  if (options && options.highlightHandler) {
453    options.highlightHandler(dwr.util.byId(ele));
454  }
455  else if (dwr.util._highlightHandler != null) {
456    dwr.util._highlightHandler(dwr.util.byId(ele));
457  }
458};
459
460/**
461 * Set the value an HTML element to the specified value.
462 * @see http://getahead.org/dwr/browser/util/setvalue
463 */
464dwr.util.setValue = function(ele, val, options) {
465  if (val == null) val = "";
466  if (options == null) options = {};
467
468  var orig = ele;
469  if (typeof ele == "string") {
470    ele = dwr.util.byId(ele);
471    // We can work with names and need to sometimes for radio buttons, and IE has
472    // an annoying bug where getElementById() returns an element based on name if
473    // it doesn't find it by id. Here we don't want to do that, so:
474    if (ele && ele.id != orig) ele = null;
475  }
476  var nodes = null;
477  if (ele == null) {
478    // Now it is time to look by name
479    nodes = document.getElementsByName(orig);
480    if (nodes.length >= 1) ele = nodes.item(0);
481  }
482
483  if (ele == null) {
484    dwr.util._debug("setValue() can't find an element with id/name: " + orig + ".");
485    return;
486  }
487
488  // All paths now lead to some update so we highlight a change
489  dwr.util.highlight(ele, options);
490
491  if (dwr.util._isHTMLElement(ele, "select")) {
492    if (ele.type == "select-multiple" && dwr.util._isArray(val)) dwr.util._selectListItems(ele, val);
493    else dwr.util._selectListItem(ele, val);
494    return;
495  }
496
497  if (dwr.util._isHTMLElement(ele, "input")) {
498    if (ele.type == "radio" || ele.type == "checkbox") {
499      if (nodes && nodes.length >= 1) {
500        for (var i = 0; i < nodes.length; i++) {
501          var node = nodes.item(i);
502          if (node.type != ele.type) continue;
503          if (dwr.util._isArray(val)) {
504            node.checked = false;
505            for (var j = 0; j < val.length; j++)
506              if (val[j] == node.value) node.checked = true;
507          }
508          else {
509            node.checked = (node.value == val);
510          }
511        }
512      }
513      else {
514        ele.checked = (val == true);
515      }
516    }
517    else ele.value = val;
518
519    return;
520  }
521
522  if (dwr.util._isHTMLElement(ele, "textarea")) {
523    ele.value = val;
524    return;
525  }
526
527  // If the value to be set is a DOM object then we try importing the node
528  // rather than serializing it out
529  if (val.nodeType) {
530    if (val.nodeType == 9 /*Node.DOCUMENT_NODE*/) val = val.documentElement;
531    val = dwr.util._importNode(ele.ownerDocument, val, true);
532    ele.appendChild(val);
533    return;
534  }
535
536  // Fall back to innerHTML and friends
537  if (dwr.util._shouldEscapeHtml(options)) {
538    if ("textContent" in ele) ele.textContent = val.toString();
539    else if ("innerText" in ele) ele.innerText = val.toString();
540    else ele.innerHTML = dwr.util.escapeHtml(val.toString());
541  }
542  else {
543    ele.innerHTML = val;
544  }
545};
546
547/**
548 * @private Find multiple items in a select list and select them. Used by setValue()
549 * @param ele The select list item
550 * @param val The array of values to select
551 */
552dwr.util._selectListItems = function(ele, val) {
553  // We deal with select list elements by selecting the matching option
554  // Begin by searching through the values
555  var found  = false;
556  var i;
557  var j;
558  for (i = 0; i < ele.options.length; i++) {
559    ele.options[i].selected = false;
560    for (j = 0; j < val.length; j++) {
561      if (ele.options[i].value == val[j]) {
562        ele.options[i].selected = true;
563      }
564    }
565  }
566  // If that fails then try searching through the visible text
567  if (found) return;
568
569  for (i = 0; i < ele.options.length; i++) {
570    for (j = 0; j < val.length; j++) {
571      if (ele.options[i].text == val[j]) {
572        ele.options[i].selected = true;
573      }
574    }
575  }
576};
577
578/**
579 * @private Find an item in a select list and select it. Used by setValue()
580 * @param ele The select list item
581 * @param val The value to select
582 */
583dwr.util._selectListItem = function(ele, val) {
584  // We deal with select list elements by selecting the matching option
585  // Begin by searching through the values
586  var found = false;
587  var i;
588  for (i = 0; i < ele.options.length; i++) {
589    if (ele.options[i].value == val) {
590      ele.options[i].selected = true;
591      found = true;
592    }
593    else {
594      ele.options[i].selected = false;
595    }
596  }
597
598  // If that fails then try searching through the visible text
599  if (found) return;
600
601  for (i = 0; i < ele.options.length; i++) {
602    ele.options[i].selected = (ele.options[i].text == val);
603  }
604};
605
606/**
607 * Read the current value for a given HTML element.
608 * @see http://getahead.org/dwr/browser/util/getvalue
609 */
610dwr.util.getValue = function(ele, options) {
611  if (options == null) options = {};
612  var orig = ele;
613  if (typeof ele == "string") {
614    ele = dwr.util.byId(ele);
615    // We can work with names and need to sometimes for radio buttons, and IE has
616    // an annoying bug where getElementById() returns an element based on name if
617    // it doesn't find it by id. Here we don't want to do that, so:
618    if (ele && ele.id != orig) ele = null;
619  }
620  var nodes = null;
621  if (ele == null) {
622    // Now it is time to look by name
623    nodes = document.getElementsByName(orig);
624    if (nodes.length >= 1) ele = nodes.item(0);
625  }
626  if (ele == null) {
627    dwr.util._debug("getValue() can't find an element with id/name: " + orig + ".");
628    return "";
629  }
630
631  if (dwr.util._isHTMLElement(ele, "select")) {
632    // Using "type" property instead of "multiple" as "type" is an official 
633    // client-side property since JS 1.1
634    if (ele.type == "select-multiple") {
635      var reply = new Array();
636      for (var i = 0; i < ele.options.length; i++) {
637        var item = ele.options[i];
638        if (item.selected) {
639          var valueAttr = item.getAttributeNode("value");
640          if (valueAttr && valueAttr.specified) {
641            reply.push(item.value);
642          }
643          else {
644            reply.push(item.text);
645          }
646        }
647      }
648      return reply;
649    }
650    else {
651      var sel = ele.selectedIndex;
652      if (sel != -1) {
653        var item = ele.options[sel];
654        var valueAttr = item.getAttributeNode("value");
655        if (valueAttr && valueAttr.specified) {
656          return item.value;
657        }
658        return item.text;
659      }
660      else {
661        return "";
662      }
663    }
664  }
665
666  if (dwr.util._isHTMLElement(ele, "input")) {
667    if (ele.type == "radio") {
668      if (nodes && nodes.length >= 1) {
669        for (var i = 0; i < nodes.length; i++) {
670          var node = nodes.item(i);
671          if (node.type == ele.type) {
672            if (node.checked) return node.value;
673          }
674        }
675      }
676      return ele.checked;
677    }
678    if (ele.type == "checkbox") {
679      if (nodes && nodes.length >= 1) {
680        var reply = [];
681        for (var i = 0; i < nodes.length; i++) {
682          var node = nodes.item(i);
683          if (node.type == ele.type) {
684            if (node.checked) reply.push(node.value);
685          }
686        }
687        return reply;
688      }
689      return ele.checked;
690    }
691    return ele.value;
692  }
693
694  if (dwr.util._isHTMLElement(ele, "textarea")) {
695    return ele.value;
696  }
697
698  if (dwr.util._shouldEscapeHtml(options)) {
699    if (ele.textContent) return ele.textContent;
700    else if (ele.innerText) return ele.innerText;
701  }
702  return ele.innerHTML;
703};
704
705/**
706 * getText() is like getValue() except that it reads the text (and not the value) from select elements
707 * @see http://getahead.org/dwr/browser/util/gettext
708 */
709dwr.util.getText = function(ele) {
710  ele = dwr.util._getElementById(ele, "getText()");
711  if (ele == null) return null;
712  if (!dwr.util._isHTMLElement(ele, "select")) {
713    dwr.util._debug("getText() can only be used with select elements. Attempt to use: " + dwr.util._detailedTypeOf(ele) + " from  id: " + orig + ".");
714    return "";
715  }
716
717  // This is a bit of a scam because it assumes single select
718  // but I'm not sure how we should treat multi-select.
719  var sel = ele.selectedIndex;
720  if (sel != -1) {
721    return ele.options[sel].text;
722  }
723  else {
724    return "";
725  }
726};
727
728/**
729 * Given a map, or a recursive structure consisting of arrays and maps, call 
730 * setValue() for all leaf entries and use intermediate levels to form nested
731 * element ids.
732 * @see http://getahead.org/dwr/browser/util/setvalues
733 */
734dwr.util.setValues = function(data, options) {
735  var prefix = "";
736  var depth = 100;
737  if (options && options.prefix) prefix = options.prefix;
738  if (options && options.idPrefix) prefix = options.idPrefix;
739  if (options && "depth" in options) depth = options.depth;
740  dwr.util._setValuesRecursive(data, prefix, depth, options);
741};
742
743/**
744 * @private Recursive helper for setValues()
745 */
746dwr.util._setValuesRecursive = function(data, idpath, depth, options) {
747  if (depth == 0) return;
748  // Array containing objects -> add "[n]" to prefix and make recursive call
749  // for each item object
750  if (dwr.util._isArray(data) && data.length > 0 && dwr.util._isObject(data[0])) {
751    for (var i = 0; i < data.length; i++) {
752      dwr.util._setValuesRecursive(data[i], idpath+"["+i+"]", depth-1, options);
753    }
754  }
755  // Object (not array) -> handle nested object properties
756  else if (dwr.util._isObject(data) && !dwr.util._isArray(data)) {
757    for (var prop in data) {
758      var subidpath = idpath ? idpath+"."+prop : prop;
759      // Object (not array), or array containing objects -> call ourselves recursively
760      if (dwr.util._isObject(data[prop]) && !dwr.util._isArray(data[prop]) && !dwr.util._isDate(data[prop]) 
761          || dwr.util._isArray(data[prop]) && data[prop].length > 0 && dwr.util._isObject(data[prop][0])) {
762        dwr.util._setValuesRecursive(data[prop], subidpath, depth-1, options);
763      }
764      // Functions -> skip
765      else if (typeof data[prop] == "function") {
766        // NOP
767      }
768      // Only simple values left (or array of simple values, or empty array)
769      // -> call setValue()
770      else {
771        // Are there any elements with that id or name
772        if (dwr.util.byId(subidpath) != null || document.getElementsByName(subidpath).length >= 1) {
773          dwr.util.setValue(subidpath, data[prop], options);
774        }
775      }
776    }
777  }
778};
779
780/**
781 * Given a map, or a recursive structure consisting of arrays and maps, call 
782 * getValue() for all leaf entries and use intermediate levels to form nested
783 * element ids.
784 * Given a string or element that refers to a form, create an object from the 
785 * elements of the form.
786 * @see http://getahead.org/dwr/browser/util/getvalues
787 */
788dwr.util.getValues = function(data, options) {
789  if (typeof data == "string" || dwr.util._isHTMLElement(data)) {
790    return dwr.util.getFormValues(data);
791  }
792  else {
793    var prefix = "";
794    var depth = 100;
795    if (options != null && options.prefix) prefix = options.prefix;
796    if (options != null && options.idPrefix) prefix = options.idPrefix;
797    if (options != null && "depth" in options) depth = options.depth;
798    dwr.util._getValuesRecursive(data, prefix, depth, options);
799    return data;
800  }
801};
802
803/**
804 * Given a string or element that refers to a form, create an object from the 
805 * elements of the form.
806 * @see http://getahead.org/dwr/browser/util/getvalues
807 */
808dwr.util.getFormValues = function(eleOrNameOrId) {
809  var ele = null;
810  if (typeof eleOrNameOrId == "string") {
811    ele = document.forms[eleOrNameOrId];
812    if (ele == null) ele = dwr.util.byId(eleOrNameOrId);
813  }
814  else if (dwr.util._isHTMLElement(eleOrNameOrId)) {
815    ele = eleOrNameOrId;
816  }
817  if (ele != null) {
818    if (ele.elements == null) {
819      alert("getFormValues() requires an object or reference to a form element.");
820      return null;
821    }
822    var reply = {};
823    var name;
824    var value;
825    for (var i = 0; i < ele.elements.length; i++) {
826      if (ele[i].type in {button:0,submit:0,reset:0,image:0,file:0}) continue;
827      if (ele[i].name) {
828        name = ele[i].name;
829        value = dwr.util.getValue(name);
830      }
831      else {
832        if (ele[i].id) name = ele[i].id;
833        else name = "element" + i;
834        value = dwr.util.getValue(ele[i]);
835      }
836      reply[name] = value;
837    }
838    return reply;
839  }
840};
841
842/**
843 * @private Recursive helper for getValues().
844 */
845dwr.util._getValuesRecursive = function(data, idpath, depth, options) {
846  if (depth == 0) return;
847  // Array containing objects -> add "[n]" to idpath and make recursive call
848  // for each item object
849  if (dwr.util._isArray(data) && data.length > 0 && dwr.util._isObject(data[0])) {
850    for (var i = 0; i < data.length; i++) {
851      dwr.util._getValuesRecursive(data[i], idpath+"["+i+"]", depth-1, options);
852    }
853  }
854  // Object (not array) -> handle nested object properties
855  else if (dwr.util._isObject(data) && !dwr.util._isArray(data)) {
856    for (var prop in data) {
857      var subidpath = idpath ? idpath+"."+prop : prop;
858      // Object, or array containing objects -> call ourselves recursively
859      if (dwr.util._isObject(data[prop]) && !dwr.util._isArray(data[prop])
860          || dwr.util._isArray(data[prop]) && data[prop].length > 0 && dwr.util._isObject(data[prop][0])) {
861        dwr.util._getValuesRecursive(data[prop], subidpath, depth-1, options);
862      }
863      // Functions -> skip
864      else if (typeof data[prop] == "function") {
865        // NOP
866      }
867      // Only simple values left (or array of simple values, or empty array)
868      // -> call getValue()
869      else {
870        // Are there any elements with that id or name
871        if (dwr.util.byId(subidpath) != null || document.getElementsByName(subidpath).length >= 1) {
872          data[prop] = dwr.util.getValue(subidpath);
873        }
874      }
875    }
876  }
877};
878
879/**
880 * Add options to a list from an array or map.
881 * @see http://getahead.org/dwr/browser/lists
882 */
883dwr.util.addOptions = function(ele, data/*, options*/) {
884  ele = dwr.util._getElementById(ele, "addOptions()");
885  if (ele == null) return;
886  var useOptions = dwr.util._isHTMLElement(ele, "select");
887  var useLi = dwr.util._isHTMLElement(ele, ["ul", "ol"]);
888  if (!useOptions && !useLi) {
889    dwr.util._debug("addOptions() can only be used with select/ul/ol elements. Attempt to use: " + dwr.util._detailedTypeOf(ele));
890    return;
891  }
892  if (data == null) return;
893  
894  var argcount = arguments.length;
895  var options = {};
896  var lastarg = arguments[argcount - 1]; 
897  if (argcount > 2 && dwr.util._isObject(lastarg)) {
898    options = lastarg;
899    argcount--;
900  }
901  var arg3 = null; if (argcount >= 3) arg3 = arguments[2];
902  var arg4 = null; if (argcount >= 4) arg4 = arguments[3];
903  if (!options.optionCreator && useOptions) options.optionCreator = dwr.util._defaultOptionCreator;
904  if (!options.optionCreator && useLi) options.optionCreator = dwr.util._defaultListItemCreator;
905  options.document = ele.ownerDocument;
906
907  var text, value, li;
908  if (dwr.util._isArray(data)) {
909    // Loop through the data that we do have
910    for (var i = 0; i < data.length; i++) {
911      options.data = data[i];
912      options.text = null;
913      options.value = null;
914      if (useOptions) {
915        if (arg3 != null) {
916          if (arg4 != null) {
917            options.text = dwr.util._getValueFrom(data[i], arg4);
918            options.value = dwr.util._getValueFrom(data[i], arg3);
919          }
920          else options.text = options.value = dwr.util._getValueFrom(data[i], arg3);
921        }
922        else options.text = options.value = dwr.util._getValueFrom(data[i]);
923
924        if (options.text != null || options.value) {
925          var opt = options.optionCreator(options);
926          opt.text = options.text;
927          opt.value = options.value;
928          ele.options[ele.options.length] = opt;
929        }
930      }
931      else {
932        options.value = dwr.util._getValueFrom(data[i], arg3);
933        if (options.value != null) {
934          li = options.optionCreator(options);
935          if (dwr.util._shouldEscapeHtml(options)) {
936            options.value = dwr.util.escapeHtml(options.value);
937          }
938          li.innerHTML = options.value;
939          ele.appendChild(li);
940        }
941      }
942    }
943  }
944  else if (arg4 != null) {
945    if (!useOptions) {
946      alert("dwr.util.addOptions can only create select lists from objects.");
947      return;
948    }
949    for (var prop in data) {
950      options.data = data[prop];
951      options.value = dwr.util._getValueFrom(data[prop], arg3);
952      options.text = dwr.util._getValueFrom(data[prop], arg4);
953
954      if (options.text != null || options.value) {
955        var opt = options.optionCreator(options);
956        opt.text = options.text;
957        opt.value = options.value;
958        ele.options[ele.options.length] = opt;
959      }
960    }
961  }
962  else {
963    if (!useOptions) {
964      dwr.util._debug("dwr.util.addOptions can only create select lists from objects.");
965      return;
966    }
967    for (var prop in data) {
968      if (typeof data[prop] == "function") continue;
969      options.data = data[prop];
970      if (!arg3) {
971        options.value = prop;
972        options.text = data[prop];
973      }
974      else {
975        options.value = data[prop];
976        options.text = prop;
977      }
978      if (options.text != null || options.value) {
979        var opt = options.optionCreator(options);
980        opt.text = options.text;
981        opt.value = options.value;
982        ele.options[ele.options.length] = opt;
983      }
984    }
985  }
986
987  // All error routes through this function result in a return, so highlight now
988  dwr.util.highlight(ele, options); 
989};
990
991/**
992 * @private Get the data from an array function for dwr.util.addOptions
993 */
994dwr.util._getValueFrom = function(data, method) {
995  if (method == null) return data;
996  else if (typeof method == 'function') return method(data);
997  else return data[method];
998};
999
1000/**
1001 * @private Default option creation function
1002 */
1003dwr.util._defaultOptionCreator = function(options) {
1004  return options.document.createElement("option");
1005};
1006
1007/**
1008 * @private Default list item creation function
1009 */
1010dwr.util._defaultListItemCreator = function(options) {
1011  return options.document.createElement("li");
1012};
1013
1014/**
1015 * Remove all the options from a select list (specified by id)
1016 * @see http://getahead.org/dwr/browser/lists
1017 */
1018dwr.util.removeAllOptions = function(ele) {
1019  ele = dwr.util._getElementById(ele, "removeAllOptions()");
1020  if (ele == null) return;
1021  var useOptions = dwr.util._isHTMLElement(ele, "select");
1022  var useLi = dwr.util._isHTMLElement(ele, ["ul", "ol"]);
1023  if (!useOptions && !useLi) {
1024    dwr.util._debug("removeAllOptions() can only be used with select, ol and ul elements. Attempt to use: " + dwr.util._detailedTypeOf(ele));
1025    return;
1026  }
1027  if (useOptions) {
1028    ele.options.length = 0;
1029  }
1030  else {
1031    while (ele.childNodes.length > 0) {
1032      ele.removeChild(ele.firstChild);
1033    }
1034  }
1035};
1036
1037/**
1038 * Create rows inside a the table, tbody, thead or tfoot element (given by id).
1039 * @see http://getahead.org/dwr/browser/tables
1040 */
1041dwr.util.addRows = function(ele, data, cellFuncs, options) {
1042  ele = dwr.util._getElementById(ele, "addRows()");
1043  if (ele == null) return;
1044  if (!dwr.util._isHTMLElement(ele, ["table", "tbody", "thead", "tfoot"])) {
1045    dwr.util._debug("addRows() can only be used with table, tbody, thead and tfoot elements. Attempt to use: " + dwr.util._detailedTypeOf(ele));
1046    return;
1047  }
1048  if (!options) options = {};
1049  if (!options.rowCreator) options.rowCreator = dwr.util._defaultRowCreator;
1050  if (!options.cellCreator) options.cellCreator = dwr.util._defaultCellCreator;
1051  options.document = ele.ownerDocument;
1052  var tr, rowNum;
1053  if (dwr.util._isArray(data)) {
1054    for (rowNum = 0; rowNum < data.length; rowNum++) {
1055      options.rowData = data[rowNum];
1056      options.rowIndex = rowNum;
1057      options.rowNum = rowNum;
1058      options.data = null;
1059      options.cellNum = -1;
1060      tr = dwr.util._addRowInner(cellFuncs, options);
1061      if (tr != null) ele.appendChild(tr);
1062    }
1063  }
1064  else if (typeof data == "object") {
1065    rowNum = 0;
1066    for (var rowIndex in data) {
1067      options.rowData = data[rowIndex];
1068      options.rowIndex = rowIndex;
1069      options.rowNum = rowNum;
1070      options.data = null;
1071      options.cellNum = -1;
1072      tr = dwr.util._addRowInner(cellFuncs, options);
1073      if (tr != null) ele.appendChild(tr);
1074      rowNum++;
1075    }
1076  }
1077
1078  dwr.util.highlight(ele, options);
1079};
1080
1081/**
1082 * @private Internal function to draw a single row of a table.
1083 */
1084dwr.util._addRowInner = function(cellFuncs, options) {
1085  var tr = options.rowCreator(options);
1086  if (tr == null) return null;
1087  for (var cellNum = 0; cellNum < cellFuncs.length; cellNum++) {
1088    var func = cellFuncs[cellNum];
1089    if (typeof func == 'function') options.data = func(options.rowData, options);
1090    else options.data = func || "";
1091    options.cellNum = cellNum;
1092    var td = options.cellCreator(options);
1093    if (td != null) {
1094      if (options.data != null) {
1095        if (dwr.util._isHTMLElement(options.data)) td.appendChild(options.data);
1096        else {
1097          if (dwr.util._shouldEscapeHtml(options) && typeof(options.data) == "string") {
1098            td.innerHTML = dwr.util.escapeHtml(options.data);
1099          }
1100          else {
1101            td.innerHTML = options.data;
1102          }
1103        }
1104      }
1105      tr.appendChild(td);
1106    }
1107  }
1108  return tr;
1109};
1110
1111/**
1112 * @private Default row creation function
1113 */
1114dwr.util._defaultRowCreator = function(options) {
1115  return options.document.createElement("tr");
1116};
1117
1118/**
1119 * @private Default cell creation function
1120 */
1121dwr.util._defaultCellCreator = function(options) {
1122  return options.document.createElement("td");
1123};
1124
1125/**
1126 * Remove all the children of a given node.
1127 * @see http://getahead.org/dwr/browser/tables
1128 */
1129dwr.util.removeAllRows = function(ele, options) {
1130  ele = dwr.util._getElementById(ele, "removeAllRows()");
1131  if (ele == null) return;
1132  if (!options) options = {};
1133  if (!options.filter) options.filter = function() { return true; };
1134  if (!dwr.util._isHTMLElement(ele, ["table", "tbody", "thead", "tfoot"])) {
1135    dwr.util._debug("removeAllRows() can only be used with table, tbody, thead and tfoot elements. Attempt to use: " + dwr.util._detailedTypeOf(ele));
1136    return;
1137  }
1138  var child = ele.firstChild;
1139  var next;
1140  while (child != null) {
1141    next = child.nextSibling;
1142    if (options.filter(child)) {
1143      ele.removeChild(child);
1144    }
1145    child = next;
1146  }
1147};
1148
1149/**
1150 * dwr.util.byId(ele).className = "X", that we can call from Java easily.
1151 */
1152dwr.util.setClassName = function(ele, className) {
1153  ele = dwr.util._getElementById(ele, "setClassName()");
1154  if (ele == null) return;
1155  ele.className = className;
1156};
1157
1158/**
1159 * dwr.util.byId(ele).className += "X", that we can call from Java easily.
1160 */
1161dwr.util.addClassName = function(ele, className) {
1162  ele = dwr.util._getElementById(ele, "addClassName()");
1163  if (ele == null) return;
1164  ele.className += " " + className;
1165};
1166
1167/**
1168 * dwr.util.byId(ele).className -= "X", that we can call from Java easily
1169 * From code originally by Gavin Kistner
1170 */
1171dwr.util.removeClassName = function(ele, className) {
1172  ele = dwr.util._getElementById(ele, "removeClassName()");
1173  if (ele == null) return;
1174  var regex = new RegExp("(^|\\s)" + className + "(\\s|$)", 'g');
1175  ele.className = ele.className.replace(regex, '');
1176};
1177
1178/**
1179 * dwr.util.byId(ele).className |= "X", that we can call from Java easily.
1180 */
1181dwr.util.toggleClassName = function(ele, className) {
1182  ele = dwr.util._getElementById(ele, "toggleClassName()");
1183  if (ele == null) return;
1184  var regex = new RegExp("(^|\\s)" + className + "(\\s|$)");
1185  if (regex.test(ele.className)) {
1186    ele.className = ele.className.replace(regex, '');
1187  }
1188  else {
1189    ele.className += " " + className;
1190  }
1191};
1192
1193/**
1194 * Clone a node and insert it into the document just above the 'template' node
1195 * @see http://getahead.org/dwr/???
1196 */
1197dwr.util.cloneNode = function(ele, options) {
1198  ele = dwr.util._getElementById(ele, "cloneNode()");
1199  if (ele == null) return null;
1200  if (options == null) options = {};
1201  var clone = ele.cloneNode(true);
1202  if (options.idPrefix || options.idSuffix) {
1203    dwr.util._updateIds(clone, options);
1204  }
1205  else {
1206    dwr.util._removeIds(clone);
1207  }
1208  ele.parentNode.insertBefore(clone, ele);
1209  return clone;
1210};
1211
1212/**
1213 * @private Update all of the ids in an element tree
1214 */
1215dwr.util._updateIds = function(ele, options) {
1216  if (options == null) options = {};
1217  if (ele.id) {
1218    ele.setAttribute("id", (options.idPrefix || "") + ele.id + (options.idSuffix || ""));
1219  }
1220  var children = ele.childNodes;
1221  for (var i = 0; i < children.length; i++) {
1222    var child = children.item(i);
1223    if (child.nodeType == 1 /*Node.ELEMENT_NODE*/) {
1224      dwr.util._updateIds(child, options);
1225    }
1226  }
1227};
1228
1229/**
1230 * @private Remove all the Ids from an element
1231 */
1232dwr.util._removeIds = function(ele) {
1233  if (ele.id) ele.removeAttribute("id");
1234  var children = ele.childNodes;
1235  for (var i = 0; i < children.length; i++) {
1236    var child = children.item(i);
1237    if (child.nodeType == 1 /*Node.ELEMENT_NODE*/) {
1238      dwr.util._removeIds(child);
1239    }
1240  }
1241};
1242
1243/**
1244 * Clone a template node and its embedded template child nodes according to
1245 * cardinalities (of arrays) in supplied data.  
1246 */
1247dwr.util.cloneNodeForValues = function(templateEle, data, options) {
1248  templateEle = dwr.util._getElementById(templateEle, "cloneNodeForValues()");
1249  if (templateEle == null) return null;
1250  if (options == null) options = {};
1251  var idpath;
1252  if (options.idPrefix != null)
1253    idpath = options.idPrefix;
1254  else
1255    idpath = templateEle.id || ""; 
1256  return dwr.util._cloneNodeForValuesRecursive(templateEle, data, idpath, options);
1257};
1258
1259/**
1260 * @private Recursive helper for cloneNodeForValues(). 
1261 */
1262dwr.util._cloneNodeForValuesRecursive = function(templateEle, data, idpath, options) {
1263  // Incoming array -> make an id for each item and call clone of the template 
1264  // for each of them
1265  if (dwr.util._isArray(data)) {
1266    var clones = [];
1267    for (var i = 0; i < data.length; i++) {
1268      var item = data[i];
1269      var clone = dwr.util._cloneNodeForValuesRecursive(templateEle, item, idpath + "[" + i + "]", options);
1270      clones.push(clone);
1271    }
1272    return clones;
1273  }
1274  else
1275  // Incoming object (not array) -> clone the template, add id prefixes, add 
1276  // clone to DOM, and then recurse into any array properties if they contain 
1277  // objects and there is a suitable template
1278  if (dwr.util._isObject(data) && !dwr.util._isArray(data)) {
1279    var clone = templateEle.cloneNode(true);
1280    if (options.updateCloneStyle && clone.style) {
1281      for (var propname in options.updateCloneStyle) {
1282        clone.style[propname] = options.updateCloneStyle[propname];
1283      }
1284    }
1285    dwr.util._replaceIds(clone, templateEle.id, idpath);
1286    templateEle.parentNode.insertBefore(clone, templateEle);
1287    dwr.util._cloneSubArrays(data, idpath, options);
1288    return clone;
1289  }
1290
1291  // It is an error to end up here so we return nothing
1292  return null;
1293};
1294
1295/**
1296 * @private Substitute a leading idpath fragment with another idpath for all 
1297 * element ids tree, and remove ids that don't match the idpath. 
1298 */
1299dwr.util._replaceIds = function(ele, oldidpath, newidpath) {
1300  if (ele.id) {
1301    var newId = null;
1302    if (ele.id == oldidpath) {
1303      newId = newidpath;
1304    }
1305    else if (ele.id.length > oldidpath.length) {
1306      if (ele.id.substr(0, oldidpath.length) == oldidpath) {
1307        var trailingChar = ele.id.charAt(oldidpath.length);
1308        if (trailingChar == "." || trailingChar == "[") {
1309          newId = newidpath + ele.id.substr(oldidpath.length);
1310        }
1311      }
1312    }
1313    if (newId) {
1314      ele.setAttribute("id", newId);
1315    }
1316    else {
1317      ele.removeAttribute("id");
1318    }
1319  }
1320  var children = ele.childNodes;
1321  for (var i = 0; i < children.length; i++) {
1322    var child = children.item(i);
1323    if (child.nodeType == 1 /*Node.ELEMENT_NODE*/) {
1324      dwr.util._replaceIds(child, oldidpath, newidpath);
1325    }
1326  }
1327};
1328
1329/**
1330 * @private Finds arrays in supplied data and uses any corresponding template 
1331 * node to make a clone for each item in the array. 
1332 */
1333dwr.util._cloneSubArrays = function(data, idpath, options) {
1334  for (prop in data) {
1335    var value = data[prop];
1336    // Look for potential recursive cloning in all array properties
1337    if (dwr.util._isArray(value)) {
1338      // Only arrays with objects are interesting for cloning
1339      if (value.length > 0 && dwr.util._isObject(value[0])) {
1340        var subTemplateId = idpath + "." + prop;
1341        var subTemplateEle = dwr.util.byId(subTemplateId);
1342        if (subTemplateEle != null) {
1343          dwr.util._cloneNodeForValuesRecursive(subTemplateEle, value, subTemplateId, options);
1344        }
1345      }
1346    }
1347    // Continue looking for arrays in object properties
1348    else if (dwr.util._isObject(value)) {
1349      dwr.util._cloneSubArrays(value, idpath + "." + prop, options);
1350    }
1351  }
1352};
1353
1354/**
1355 * @private Helper to turn a string into an element with an error message
1356 */
1357dwr.util._getElementById = function(ele, source) {
1358  var orig = ele;
1359  ele = dwr.util.byId(ele);
1360  if (ele == null) {
1361    dwr.util._debug(source + " can't find an element with id: " + orig + ".");
1362  }
1363  return ele;
1364};
1365
1366/**
1367 * @private Is the given node an HTML element (optionally of a given type)?
1368 * @param ele The element to test
1369 * @param nodeName eg "input", "textarea" - check for node name (optional)
1370 *         if nodeName is an array then check all for a match.
1371 */
1372dwr.util._isHTMLElement = function(ele, nodeName) {
1373  if (ele == null || typeof ele != "object" || ele.nodeName == null) {
1374    return false;
1375  }
1376  if (nodeName != null) {
1377    var test = ele.nodeName.toLowerCase();
1378    if (typeof nodeName == "string") {
1379      return test == nodeName.toLowerCase();
1380    }
1381    if (dwr.util._isArray(nodeName)) {
1382      var match = false;
1383      for (var i = 0; i < nodeName.length && !match; i++) {
1384        if (test == nodeName[i].toLowerCase()) {
1385          match =  true;
1386        }
1387      }
1388      return match;
1389    }
1390    dwr.util._debug("dwr.util._isHTMLElement was passed test node name that is neither a string or array of strings");
1391    return false;
1392  }
1393  return true;
1394};
1395
1396/**
1397 * @private Like typeOf except that more information for an object is returned other than "object"
1398 */
1399dwr.util._detailedTypeOf = function(x) {
1400  var reply = typeof x;
1401  if (reply == "object") {
1402    reply = Object.prototype.toString.apply(x); // Returns "[object class]"
1403    reply = reply.substring(8, reply.length-1);  // Just get the class bit
1404  }
1405  return reply;
1406};
1407
1408/**
1409 * @private Object detector. Excluding null from objects.
1410 */
1411dwr.util._isObject = function(data) {
1412  return (data && typeof data == "object");
1413};
1414
1415/**
1416 * @private Array detector. Note: instanceof doesn't work with multiple frames.
1417 */
1418dwr.util._isArray = function(data) {
1419  return (data && data.join);
1420};
1421
1422/**
1423 * @private Date detector. Note: instanceof doesn't work with multiple frames.
1424 */
1425dwr.util._isDate = function(data) {
1426  return (data && data.toUTCString) ? true : false;
1427};
1428
1429/**
1430 * @private Used by setValue. Gets around the missing functionallity in IE.
1431 */
1432dwr.util._importNode = function(doc, importedNode, deep) {
1433  var newNode;
1434
1435  if (importedNode.nodeType == 1 /*Node.ELEMENT_NODE*/) {
1436    newNode = doc.createElement(importedNode.nodeName);
1437
1438    for (var i = 0; i < importedNode.attributes.length; i++) {
1439      var attr = importedNode.attributes[i];
1440      if (attr.nodeValue != null && attr.nodeValue != '') {
1441        newNode.setAttribute(attr.name, attr.nodeValue);
1442      }
1443    }
1444
1445    if (importedNode.style != null) {
1446      newNode.style.cssText = importedNode.style.cssText;
1447    }
1448  }
1449  else if (importedNode.nodeType == 3 /*Node.TEXT_NODE*/) {
1450    newNode = doc.createTextNode(importedNode.nodeValue);
1451  }
1452
1453  if (deep && importedNode.hasChildNodes()) {
1454    for (i = 0; i < importedNode.childNodes.length; i++) {
1455      newNode.appendChild(dwr.util._importNode(doc, importedNode.childNodes[i], true));
1456    }
1457  }
1458
1459  return newNode;
1460};
1461
1462/** @private Used internally when some message needs to get to the programmer */
1463dwr.util._debug = function(message, stacktrace) {
1464  var written = false;
1465  try {
1466    if (window.console) {
1467      if (stacktrace && window.console.trace) window.console.trace();
1468      window.console.log(message);
1469      written = true;
1470    }
1471    else if (window.opera && window.opera.postError) {
1472      window.opera.postError(message);
1473      written = true;
1474    }
1475  }
1476  catch (ex) { /* ignore */ }
1477
1478  if (!written) {
1479    var debug = document.getElementById("dwr-debug");
1480    if (debug) {
1481      var contents = message + "<br/>" + debug.innerHTML;
1482      if (contents.length > 2048) contents = contents.substring(0, 2048);
1483      debug.innerHTML = contents;
1484    }
1485  }
1486};
1487

Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.