Updated the 19 build version to 20081106
[moodle.git] / lib / javascript-static.js
blob1728c58c0de02471a12cb07b34dcd60bae97411e
1 // Miscellaneous core Javascript functions for Moodle
3 function popupchecker(msg) {
4     var testwindow = window.open('itestwin.html', '', 'width=1,height=1,left=0,top=0,scrollbars=no');
5     if (testwindow == null)
6         {alert(msg);}
7     else {
8         testwindow.close();
9     }
13 function popUpProperties(inobj) {
14 /// Legacy function
15   var op = window.open();
16   op.document.open('text/plain');
17   for (objprop in inobj) {
18     op.document.write(objprop + ' => ' + inobj[objprop] + '\n');
19   }
20   op.document.close();
23 function fillmessagebox(text) {
24 /// Legacy function
25   document.form.message.value = text;
28 function copyrichtext(textname) {
29 /// Legacy stub for old editor - to be removed soon
30   return true;
34 function checkall() {
35   var el = document.getElementsByTagName('input');
36   for(var i=0; i<el.length; i++) {
37     if(el[i].type == 'checkbox') {
38       el[i].checked = true;
39     }
40   }
43 function checknone() {
44   var el = document.getElementsByTagName('input');
45   for(var i=0; i<el.length; i++) {
46     if(el[i].type == 'checkbox') {
47       el[i].checked = false;
48     }
49   }
52 function lockoptions(formid, master, subitems) {
53   // Subitems is an array of names of sub items.
54   // Optionally, each item in subitems may have a
55   // companion hidden item in the form with the
56   // same name but prefixed by "h".
57   var form = document.forms[formid];
59   if (eval("form."+master+".checked")) {
60     for (i=0; i<subitems.length; i++) {
61       unlockoption(form, subitems[i]);
62     }
63   } else {
64     for (i=0; i<subitems.length; i++) {
65       lockoption(form, subitems[i]);
66     }
67   }
68   return(true);
71 function lockoption(form,item) {
72   eval("form."+item+".disabled=true");/* IE thing */
73   if(form.elements['h'+item]) {
74     eval("form.h"+item+".value=1");
75   }
78 function unlockoption(form,item) {
79   eval("form."+item+".disabled=false");/* IE thing */
80   if(form.elements['h'+item]) {
81     eval("form.h"+item+".value=0");
82   }
86 function lockoptionsall(formid) {
87     var form = document.forms[formid];
88     var dependons = eval(formid+'items');
89     var tolock = Array();
90     for (var dependon in dependons) {
91         // change for MooTools compatibility
92         if (!dependons.propertyIsEnumerable(dependon)) {
93             continue;
94         }
95         var master = form[dependon];
96         if (master === undefined) {
97             continue;
98         }
99         for (var condition in dependons[dependon]) {
100             for (var value in dependons[dependon][condition]) {
101                 var lock;
102                 switch (condition) {
103                   case 'notchecked':
104                       lock = !master.checked; break;
105                   case 'checked':
106                       lock = master.checked; break;
107                   case 'noitemselected':
108                       lock = master.selectedIndex==-1; break;
109                   case 'eq':
110                       lock = master.value==value; break;
111                   default:
112                       lock = master.value!=value; break;
113                 }
114                 for (var ei in dependons[dependon][condition][value]) {
115                     // change for MooTools compatibility
116                     if (!window.webkit && (!dependons[dependon][condition][value].propertyIsEnumerable(ei))) {
117                         continue;
118                     }
119                     var eltolock = dependons[dependon][condition][value][ei];
120                     if (tolock[eltolock] != null){
121                         tolock[eltolock] =
122                                 lock || tolock[eltolock];
123                     } else {
124                         tolock[eltolock] = lock;
125                     }
126                 }
127             }
128         }
129     }
130     for (var el in tolock){
131         // change for MooTools compatibility
132         if (!tolock.propertyIsEnumerable(el)) {
133             continue;
134         }
135         var formelement = form[el];
136         if ((formelement === undefined) || (formelement.disabled === undefined)) {
137             continue;
138         }
139         formelement.disabled = tolock[el];
140     }
141     return true;
144 function lockoptionsallsetup(formid) {
145     var form = document.forms[formid];
146     var dependons = eval(formid+'items');
147     for (var dependon in dependons) {
148         // change for MooTools compatibility
149         if (!dependons.propertyIsEnumerable(dependon)) {
150             continue;
151         }
152         var master = form[dependon];
153         if (master === undefined) {
154             continue;
155         }
156         master.formid = formid;
157         master.onclick  = function() {return lockoptionsall(this.formid);};
158         master.onblur   = function() {return lockoptionsall(this.formid);};
159         master.onchange = function() {return lockoptionsall(this.formid);};
160     }
161     for (var i = 0; i < form.elements.length; i++){
162         var formelement = form.elements[i];
163         if (formelement.type=='reset') {
164             formelement.formid = formid;
165             formelement.onclick  = function() {this.form.reset();return lockoptionsall(this.formid);};
166             formelement.onblur   = function() {this.form.reset();return lockoptionsall(this.formid);};
167             formelement.onchange = function() {this.form.reset();return lockoptionsall(this.formid);};
168         }
169     }
170     return lockoptionsall(formid);
174 function submitFormById(id) {
175     var theform = document.getElementById(id);
176     if(!theform) {
177         return false;
178     }
179     if(theform.tagName.toLowerCase() != 'form') {
180         return false;
181     }
182     if(!theform.onsubmit || theform.onsubmit()) {
183         return theform.submit();
184     }
187 function select_all_in(elTagName, elClass, elId) {
188     var inputs = document.getElementsByTagName('input');
189     inputs = filterByParent(inputs, function(el) {return findParentNode(el, elTagName, elClass, elId);});
190     for(var i = 0; i < inputs.length; ++i) {
191         if(inputs[i].type == 'checkbox' || inputs[i].type == 'radio') {
192             inputs[i].checked = 'checked';
193         }
194     }
197 function deselect_all_in(elTagName, elClass, elId) {
198     var inputs = document.getElementsByTagName('INPUT');
199     inputs = filterByParent(inputs, function(el) {return findParentNode(el, elTagName, elClass, elId);});
200     for(var i = 0; i < inputs.length; ++i) {
201         if(inputs[i].type == 'checkbox' || inputs[i].type == 'radio') {
202             inputs[i].checked = '';
203         }
204     }
207 function confirm_if(expr, message) {
208     if(!expr) {
209         return true;
210     }
211     return confirm(message);
216     findParentNode (start, elementName, elementClass, elementID)
218     Travels up the DOM hierarchy to find a parent element with the
219     specified tag name, class, and id. All conditions must be met,
220     but any can be ommitted. Returns the BODY element if no match
221     found.
223 function findParentNode(el, elName, elClass, elId) {
224     while(el.nodeName.toUpperCase() != 'BODY') {
225         if(
226             (!elName || el.nodeName.toUpperCase() == elName) &&
227             (!elClass || el.className.indexOf(elClass) != -1) &&
228             (!elId || el.id == elId))
229         {
230             break;
231         }
232         el = el.parentNode;
233     }
234     return el;
237     findChildNode (start, elementName, elementClass, elementID)
239     Travels down the DOM hierarchy to find all child elements with the
240     specified tag name, class, and id. All conditions must be met,
241     but any can be ommitted.
242     Doesn't examine children of matches.
244 function findChildNodes(start, tagName, elementClass, elementID, elementName) {
245     var children = new Array();
246     for (var i = 0; i < start.childNodes.length; i++) {
247         var classfound = false;
248         var child = start.childNodes[i];
249         if((child.nodeType == 1) &&//element node type
250                   (elementClass && (typeof(child.className)=='string'))){
251             var childClasses = child.className.split(/\s+/);
252             for (var childClassIndex in childClasses){
253                 if (childClasses[childClassIndex]==elementClass){
254                     classfound = true;
255                     break;
256                 }
257             }
258         }
259         if(child.nodeType == 1) { //element node type
260             if  ( (!tagName || child.nodeName == tagName) &&
261                 (!elementClass || classfound)&&
262                 (!elementID || child.id == elementID) &&
263                 (!elementName || child.name == elementName))
264             {
265                 children = children.concat(child);
266             } else {
267                 children = children.concat(findChildNodes(child, tagName, elementClass, elementID, elementName));
268             }
269         }
270     }
271     return children;
274     elementSetHide (elements, hide)
276     Adds or removes the "hide" class for the specified elements depending on boolean hide.
278 function elementShowAdvanced(elements, show) {
279     for (var elementIndex in elements){
280         element = elements[elementIndex];
281         element.className = element.className.replace(new RegExp(' ?hide'), '')
282         if(!show) {
283             element.className += ' hide';
284         }
285     }
288 function showAdvancedInit(addBefore, nameAttr, buttonLabel, hideText, showText) {
289     var showHideButton = document.createElement("input");
290     showHideButton.type = 'button';
291     showHideButton.value = buttonLabel;
292     showHideButton.name = nameAttr;
293     showHideButton.moodle = {
294         hideLabel: hideText,
295         showLabel: showText
296     };
297     YAHOO.util.Event.addListener(showHideButton, 'click', showAdvancedOnClick);
298     el = document.getElementById(addBefore);
299     el.parentNode.insertBefore(showHideButton, el);
302 function showAdvancedOnClick(e) {
303     var button = e.target ? e.target : e.srcElement;
305     var toSet=findChildNodes(button.form, null, 'advanced');
306     var buttontext = '';
307     if (button.form.elements['mform_showadvanced_last'].value == '0' ||  button.form.elements['mform_showadvanced_last'].value == '' ) {
308         elementShowAdvanced(toSet, true);
309         buttontext = button.moodle.hideLabel;
310         button.form.elements['mform_showadvanced_last'].value = '1';
311     } else {
312         elementShowAdvanced(toSet, false);
313         buttontext = button.moodle.showLabel;
314         button.form.elements['mform_showadvanced_last'].value = '0';
315     }
316     var formelements = button.form.elements;
317     // Fixed MDL-10506
318     for (var i = 0; i < formelements.length; i++){
319         if (formelements[i] && formelements[i].name && (formelements[i].name=='mform_showadvanced')){
320             formelements[i].value = buttontext;
321         }
322     }
323     //never submit the form if js is enabled.
324     return false;
327 function unmaskPassword(id) {
328   var pw = document.getElementById(id);
329   var chb = document.getElementById(id+'unmask');
331   try {
332     // first try IE way - it can not set name attribute later
333     if (chb.checked) {
334       var newpw = document.createElement('<input type="text" name="'+pw.name+'">');
335     } else {
336       var newpw = document.createElement('<input type="password" name="'+pw.name+'">');
337     }
338     newpw.attributes['class'].nodeValue = pw.attributes['class'].nodeValue;
339   } catch (e) {
340     var newpw = document.createElement('input');
341     newpw.setAttribute('name', pw.name);
342     if (chb.checked) {
343       newpw.setAttribute('type', 'text');
344     } else {
345       newpw.setAttribute('type', 'password');
346     }
347     newpw.setAttribute('class', pw.getAttribute('class'));
348   }
349   newpw.id = pw.id;
350   newpw.size = pw.size;
351   newpw.onblur = pw.onblur;
352   newpw.onchange = pw.onchange;
353   newpw.value = pw.value;
354   pw.parentNode.replaceChild(newpw, pw);
358     elementToggleHide (element, elementFinder)
360     If elementFinder is not provided, toggles the "hidden" class for the specified element.
361     If elementFinder is provided, then the "hidden" class will be toggled for the object
362     returned by the function call elementFinder(element).
364     If persistent == true, also sets a cookie for this.
366 function elementToggleHide(el, persistent, elementFinder, strShow, strHide) {
367     if(!elementFinder) {
368         var obj = el;  //el:container
369         el = document.getElementById('togglehide_'+obj.id);
370     }
371     else {
372         var obj = elementFinder(el);  //el:button.
373     }
374     if(obj.className.indexOf('hidden') == -1) {
375         obj.className += ' hidden';
376         if (el.src) {
377             el.src = el.src.replace('switch_minus', 'switch_plus');
378             el.alt = strShow;
379             el.title = strShow;
380         }
381         var shown = 0;
382     }
383     else {
384         obj.className = obj.className.replace(new RegExp(' ?hidden'), '');
385         if (el.src) {
386             el.src = el.src.replace('switch_plus', 'switch_minus');
387             el.alt = strHide;
388             el.title = strHide;
389         }
390         var shown = 1;
391     }
393     if(persistent == true) {
394         new cookie('hide:' + obj.id, 1, (shown ? -1 : 356), '/').set();
395     }
398 function elementCookieHide(id, strShow, strHide) {
399     var obj  = document.getElementById(id);
400     var cook = new cookie('hide:' + id).read();
401     if(cook != null) {
402         elementToggleHide(obj, false, null, strShow, strHide);
403     }
406 function filterByParent(elCollection, parentFinder) {
407     var filteredCollection = [];
408     for(var i = 0; i < elCollection.length; ++i) {
409         var findParent = parentFinder(elCollection[i]);
410         if(findParent.nodeName != 'BODY') {
411             filteredCollection.push(elCollection[i]);
412         }
413     }
414     return filteredCollection;
418     All this is here just so that IE gets to handle oversized blocks
419     in a visually pleasing manner. It does a browser detect. So sue me.
422 function fix_column_widths() {
423     var agt = navigator.userAgent.toLowerCase();
424     if ((agt.indexOf("msie") != -1) && (agt.indexOf("opera") == -1)) {
425         fix_column_width('left-column');
426         fix_column_width('right-column');
427     }
430 function fix_column_width(colName) {
431     if(column = document.getElementById(colName)) {
432         if(!column.offsetWidth) {
433             setTimeout("fix_column_width('" + colName + "')", 20);
434             return;
435         }
437         var width = 0;
438         var nodes = column.childNodes;
440         for(i = 0; i < nodes.length; ++i) {
441             if(nodes[i].className.indexOf("sideblock") != -1 ) {
442                 if(width < nodes[i].offsetWidth) {
443                     width = nodes[i].offsetWidth;
444                 }
445             }
446         }
448         for(i = 0; i < nodes.length; ++i) {
449             if(nodes[i].className.indexOf("sideblock") != -1 ) {
450                 nodes[i].style.width = width + 'px';
451             }
452         }
453     }
458    Insert myValue at current cursor position
459  */
460 function insertAtCursor(myField, myValue) {
461     // IE support
462     if (document.selection) {
463         myField.focus();
464         sel = document.selection.createRange();
465         sel.text = myValue;
466     }
467     // Mozilla/Netscape support
468     else if (myField.selectionStart || myField.selectionStart == '0') {
469         var startPos = myField.selectionStart;
470         var endPos = myField.selectionEnd;
471         myField.value = myField.value.substring(0, startPos)
472             + myValue + myField.value.substring(endPos, myField.value.length);
473     } else {
474         myField.value += myValue;
475     }
480         Call instead of setting window.onload directly or setting body onload=.
481         Adds your function to a chain of functions rather than overwriting anything
482         that exists.
484 function addonload(fn) {
485     var oldhandler=window.onload;
486     window.onload=function() {
487         if(oldhandler) oldhandler();
488             fn();
489     }