1/* (c) Copyright by authors of the Tiki Wiki CMS Groupware Project 2 * 3 * All Rights Reserved. See copyright.txt for details and a complete list of authors. 4 * Licensed under the GNU LESSER GENERAL PUBLIC LICENSE. See license.txt for details. 5 * $Id$ 6 */ 7 8 9jQuery.validator.setDefaults({ 10 onkeyup: false, 11 errorClass: 'invalid-feedback', 12 errorPlacement: function(error, element) { 13 if ($(element).parents('.input-group').length > 0) { 14 error.insertAfter($(element).parents('.input-group').first()); 15 } else { 16 error.appendTo($(element).parent()); 17 } 18 }, 19 highlight: function(element) { 20 $(element).addClass('is-invalid'); 21 // Highlight chosen element if exists 22 $("#" + element.getAttribute("id") + "_chosen").addClass("is-invalid"); 23 }, 24 unhighlight: function(element) { 25 $(element).removeClass("is-invalid"); 26 // Unhighlight chosen element if exists 27 $("#" + element.getAttribute("id") + "_chosen").removeClass("is-invalid"); 28 }, 29 ignore: '.ignore' 30}); 31 32 33// see http://stackoverflow.com/questions/1300994/ 34 35jQuery.validator.addMethod("required_in_group", function (value, element, options) { 36 var numberRequired = options[0], excluded; 37 var selector = options[1]; 38 if (typeof options[2] != 'undefined') { 39 excluded = options[2]; 40 } else { 41 excluded = ''; 42 } 43 //Look for our selector within the parent form 44 var validOrNot = $(selector, element.form).filter( 45 function () { 46 // for the case where there is a other option, to allow users to 47 // jump to the other form input without trigger the validation 48 if ($(this).data('tiki_never_visited')) return 'dummy-value-for-validation'; 49 // Each field is kept if it has a value 50 return ($(this).val() && $(this).val().toLowerCase() != excluded); 51 // Set to true if there are enough, else to false 52 }).length >= numberRequired; 53 54 var validator = this; 55 // The elegent part - this element needs to check the others that match the 56 // selector, but we don't want to set off a feedback loop where each element 57 // has to check each other element. It would be like: 58 // Element 1: "I might be valid if you're valid. Are you?" 59 // Element 2: "Let's see. I might be valid if YOU'RE valid. Are you?" 60 // Element 1: "Let's see. I might be valid if YOU'RE valid. Are you?" 61 // ...etc, until we get a "too much recursion" error. 62 // 63 // So instead we 64 // 1) Flag all matching elements as 'currently being validated' 65 // using jQuery's .data() 66 // 2) Re-run validation on each of them. Since the others are now 67 // flagged as being in the process, they will skip this section, 68 // and therefore won't turn around and validate everything else 69 // 3) Once that's done, we remove the 'currently being validated' flag 70 // from all the elements 71 if (!$(element).data('being_validated')) { 72 var fields = $(selector, element.form); 73 fields.data('being_validated', true); 74 // .valid() means "validate using all applicable rules" (which 75 // includes this one) 76 validator.valid(); 77 fields.data('being_validated', false); 78 } 79 80 return validOrNot; 81 82 // {0} below is the 0th item in the options field 83}, jQuery.validator.format(tr("Please fill out {0} of these fields."))); 84 85// for validating tracker file attachments based on required_in_group 86// similar but needs a different message 87 88jQuery.validator.addMethod("required_tracker_file", function (value, element, options) { 89 var numberRequired = options[0]; 90 var selector = options[1]; 91 var validOrNot = $(selector, element.form).filter( 92 function () { 93 return $(this).val(); 94 }).length >= numberRequired; 95 96 if (!$(element).data('being_validated')) { 97 var fields = $(selector, element.form); 98 fields.data('being_validated', true); 99 fields.valid(); 100 fields.data('being_validated', false); 101 } 102 return validOrNot; 103}, jQuery.validator.format("File required")); 104 105// for validating email fields where multiple addresses can be entered
106// separator is options[0] and defaults to comma 107 108jQuery.validator.addMethod("email_multi", function (value, element, options) { 109 var separator = options[0] || ","; 110 var emails = $(element).val().split(separator); 111 112 for (var i = 0; i < emails.length; i++) { 113 if (!$.validator.methods["email"].call( this, $.trim(emails[i]), element )) { 114 return false; 115 } 116 } 117 118 return true; 119 120}, jQuery.validator.format("Please enter valid email addresses separated by commas")); 121 122jQuery.validator.addClassRules("email_multi", { 123 email_multi: true 124}); 125 126/** 127 * Wait for AJAX form validation to finish before proceeding with submit 128 * 129 * @param form form element 130 * @param event submission event (optional) 131 * @return {Boolean} 132 */ 133function process_submit(form, event) { 134 135 var $form = $(form); 136 if (!$form.attr("is_validating")) { 137 $form.attr("is_validating", true); 138 $form.validate(); 139 } 140 if ($form.validate().pendingRequest > 0) { 141 $(form).data("resubmit", true); 142 setTimeout(function() {process_submit(form, event);}, 500); 143 return false; 144 } 145 $form.attr("is_validating", false); 146 147 if (!$form.valid()) { 148 return false; 149 } 150 151 // soft-disable submit button(s) 152 if ($form.data("ajax")) { 153 $form.find("input[type=submit]").css("opacity", 0.3); 154 $form.parents(".modal").find(".auto-btn").css("opacity", 0.3); 155 } else { 156 $form.find("input[type=submit]").off("click").css("opacity", 0.3); 157 $form.parents(".modal").find(".auto-btn").off("click").css("opacity", 0.3); 158 } 159 if( $(form).hasClass("confirm-action") ) { 160 $form.tikiModal(tr("Saving...")); 161 } 162 // prevent form from submitting twice 163 if (!$form.data('submitted')) { 164 $form.data('submitted', true); 165 } else { 166 return false; 167 } 168 // deal with ajax validation submission function not sending the value of the button that submitted the form (only really happend with legacy tracker insertion screens) 169 if( typeof event !== 'undefined' && event.target ) { 170 var btn = $(event.target); 171 if (btn.is('form')) { 172 var btnform = btn; 173 var btn = btnform.find("input[type=submit]:focus"); 174 // workaround for safari 175 if( btn.length == 0 ) { 176 btn = btnform.find("input[type=submit]:first"); 177 } 178 } 179 $( "<input type='hidden'/>" ) 180 .attr( "name", btn.attr('name') ) 181 .val( btn.val() ) 182 .appendTo( $form ); 183 } 184 if( $form.data("resubmit") ) { 185 $form.data("resubmit", false); 186 $form.submit(); 187 } 188 // if the form is using ajax, send the request here instead of letting the form submit 189 if ($form.data("ajax")) { 190 if ($form.data("ajax_action") == "update") { 191 $form.tracker_update_item({ 192 trackerId: $form.data('tracker_id'), 193 itemId: $form.data('item_id'), 194 ajax: true 195 }, function(trackerInfo) { 196 // soft-reenable submit 197 $form.data('submitted', false); 198 $form.find("input[type=submit]").off("click").css("opacity", 1); 199 $form.parents(".modal").find(".auto-btn").off("click").css("opacity", 1); 200 }); 201 } else { 202 $form.tracker_insert_item({ 203 trackerId: $form.data('tracker_id'), 204 ajax: true 205 }, function(trackerInfo) { 206 // soft-reenable submit 207 $form.data("ajax_action", "update"); 208 $form.data('item_id', trackerInfo.itemId); 209 $form.data('submitted', false); 210 $form.find("input[type=submit]").off("click").css("opacity", 1); 211 $form.parents(".modal").find(".auto-btn").off("click").css("opacity", 1); 212 }); 213 } 214 return false; 215 } 216 return true; 217} 218 219jQuery.validator.addMethod("validate_cron_runtime", function (value, element, options) { 220 var cronTime = value.trim(); 221 var regex = "^(\\*|((\\*\\/)?[1-5]?[0-9])|[1-5]?[0-9]-[1-5]?[0-9]|[1-5]?[0-9](,[1-5]?[0-9])*) (\\*|((\\*\\/)?(1?[0-9]|2[0-3]))|(1?[0-9]|2[0-3])-(1?[0-9]|2[0-3])|(1?[0-9]|2[0-3])(,(1?[0-9]|2[0-3]))*) (\\*|((\\*\\/)?([1-9]|[12][0-9]|3[0-1]))|([1-9]|[12][0-9]|3[0-1])-([1-9]|[12][0-9]|3[0-1])|([1-9]|[12][0-9]|3[0-1])(,([1-9]|[12][0-9]|3[0-1]))*) (\\*|((\\*\\/)?([1-9]|1[0-2])|([1-9]|1[0-2])-([1-9]|1[0-2])|([1-9]|1[0-2])(,([1-9]|1[0-2]))*)) (\\*|((\\*\\/)?[0-6])|[0-6](,[0-6])*|[0-6]-[0-6])$"; 222 if (cronTime.match(regex) === null) { 223 $(element).addClass('is-invalid'); 224 return false;
225 } 226 $(element).parents('.form-group').first().removeClass('is-invalid'); 227 return true; 228}, jQuery.validator.format(tr("Cron run time is not valid")));
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.