vendor: 16,340 bytes, lines 1-419
1/*! 2 * jQuery Validation Plugin v1.17.0 3 * 4 * https://jqueryvalidation.org/ 5 * 6 * Copyright (c) 2017 Jörn Zaefferer 7 * Released under the MIT license 8 */ 9(function (factory) { 10 if (typeof define === "function" && define.amd) { 11 define(["jquery"], factory); 12 } else if (typeof module === "object" && module.exports) { 13 module.exports = factory(require("jquery")); 14 } else { 15 factory(jQuery); 16 } 17}(function ($) { 18 19 $.extend($.fn, { 20 21 // https://jqueryvalidation.org/validate/ 22 validate: function (options) { 23 24 // If nothing is selected, return nothing; can't chain anyway 25 if (!this.length) { 26 if (options && options.debug && window.console) { 27 console.warn("Nothing selected, can't validate, returning nothing."); 28 } 29 return; 30 } 31 32 // Check if a validator for this form was already created 33 var validator = $.data(this[0], "validator"); 34 if (validator) { 35 return validator; 36 } 37 38 // Add novalidate tag if HTML5. 39 this.attr("novalidate", "novalidate"); 40 41 validator = new $.validator(options, this[0]); 42 $.data(this[0], "validator", validator); 43 44 if (validator.settings.onsubmit) { 45 46 this.on("click.validate", ":submit", function (event) { 47 48 // Track the used submit button to properly handle scripted 49 // submits later. 50 validator.submitButton = event.currentTarget; 51 52 // Allow suppressing validation by adding a cancel class to the submit button 53 if ($(this).hasClass("cancel")) { 54 validator.cancelSubmit = true; 55 } 56 57 // Allow suppressing validation by adding the html5 formnovalidate attribute to the submit button 58 if ($(this).attr("formnovalidate") !== undefined) { 59 validator.cancelSubmit = true; 60 } 61 }); 62 63 // Validate the form on submit 64 this.on("submit.validate", function (event) { 65 if (validator.settings.debug) { 66 67 // Prevent form submit to be able to see console output 68 event.preventDefault(); 69 } 70 71 function handle() { 72 var hidden, result; 73 74 // Insert a hidden input as a replacement for the missing submit button 75 // The hidden input is inserted in two cases: 76 // - A user defined a `submitHandler` 77 // - There was a pending request due to `remote` method and `stopRequest()` 78 // was called to submit the form in case it's valid 79 if (validator.submitButton && ( validator.settings.submitHandler || validator.formSubmitted )) { 80 hidden = $("<input type='hidden'/>") 81 .attr("name", validator.submitButton.name) 82 .val($(validator.submitButton).val()) 83 .appendTo(validator.currentForm); 84 } 85 86 if (validator.settings.submitHandler) { 87 result = validator.settings.submitHandler.call(validator, validator.currentForm, event); 88 if (hidden) { 89 90 // And clean up afterwards; thanks to no-block-scope, hidden can be referenced 91 hidden.remove(); 92 } 93 if (result !== undefined) { 94 return result; 95 } 96 return false; 97 } 98 return true; 99 } 100 101 // Prevent submit for invalid forms or custom submit handlers 102 if (validator.cancelSubmit) { 103 validator.cancelSubmit = false; 104 return handle(); 105 } 106 if (validator.form()) { 107 if (validator.pendingRequest) { 108 validator.formSubmitted = true; 109 return false; 110 } 111 return handle(); 112 } else { 113 validator.focusInvalid(); 114 return false; 115 } 116 }); 117 } 118 119 return validator; 120 }, 121 122 // https://jqueryvalidation.org/valid/ 123 valid: function () { 124 var valid, validator, errorList; 125 126 if ($(this[0]).is("form")) { 127 valid = this.validate().form(); 128 } else { 129 errorList = []; 130 valid = true; 131 validator = $(this[0].form).validate(); 132 this.each(function () { 133 valid = validator.element(this) && valid; 134 if (!valid) { 135 errorList = errorList.concat(validator.errorList); 136 } 137 }); 138 validator.errorList = errorList; 139 } 140 return valid; 141 }, 142 143 // https://jqueryvalidation.org/rules/ 144 rules: function (command, argument) { 145 var element = this[0], 146 settings, staticRules, existingRules, data, param, filtered; 147 148 // If nothing is selected, return empty object; can't chain anyway 149 if (element == null) { 150 return; 151 } 152 153 if (!element.form && element.hasAttribute("contenteditable")) { 154 element.form = this.closest("form")[0]; 155 element.name = this.attr("name"); 156 } 157 158 if (element.form == null) { 159 return; 160 } 161 162 if (command) { 163 settings = $.data(element.form, "validator").settings; 164 staticRules = settings.rules; 165 existingRules = $.validator.staticRules(element); 166 switch (command) { 167 case "add": 168 $.extend(existingRules, $.validator.normalizeRule(argument)); 169 170 // Remove messages from rules, but allow them to be set separately 171 delete existingRules.messages; 172 staticRules[element.name] = existingRules; 173 if (argument.messages) { 174 settings.messages[element.name] = $.extend(settings.messages[element.name], argument.messages); 175 } 176 break; 177 case "remove": 178 if (!argument) { 179 delete staticRules[element.name]; 180 return existingRules; 181 } 182 filtered = {}; 183 $.each(argument.split(/\s/), function (index, method) { 184 filtered[method] = existingRules[method]; 185 delete existingRules[method]; 186 }); 187 return filtered; 188 } 189 } 190 191 data = $.validator.normalizeRules( 192 $.extend( 193 {}, 194 $.validator.classRules(element), 195 $.validator.attributeRules(element), 196 $.validator.dataRules(element), 197 $.validator.staticRules(element) 198 ), element); 199 200 // Make sure required is at front 201 if (data.required) { 202 param = data.required; 203 delete data.required; 204 data = $.extend({required: param}, data); 205 } 206 207 // Make sure remote is at back 208 if (data.remote) { 209 param = data.remote; 210 delete data.remote; 211 data = $.extend(data, {remote: param}); 212 } 213 214 return data; 215 } 216 }); 217 218// Custom selectors 219 $.extend($.expr.pseudos || $.expr[":"], { // '|| $.expr[ ":" ]' here enables backwards compatibility to jQuery 1.7. Can be removed when dropping jQ 1.7.x support 220 221 // https://jqueryvalidation.org/blank-selector/ 222 blank: function (a) { 223 return !$.trim("" + $(a).val()); 224 }, 225 226 // https://jqueryvalidation.org/filled-selector/ 227 filled: function (a) { 228 var val = $(a).val(); 229 return val !== null && !!$.trim("" + val); 230 }, 231 232 // https://jqueryvalidation.org/unchecked-selector/ 233 unchecked: function (a) { 234 return !$(a).prop("checked"); 235 } 236 }); 237 238// Constructor for validator 239 $.validator = function (options, form) { 240 this.settings = $.extend(true, {}, $.validator.defaults, options); 241 this.currentForm = form; 242 this.init(); 243 }; 244 245// https://jqueryvalidation.org/jQuery.validator.format/ 246 $.validator.format = function (source, params) { 247 if (arguments.length === 1) { 248 return function () { 249 var args = $.makeArray(arguments); 250 args.unshift(source); 251 return $.validator.format.apply(this, args); 252 }; 253 } 254 if (params === undefined) { 255 return source; 256 } 257 if (arguments.length > 2 && params.constructor !== Array) { 258 params = $.makeArray(arguments).slice(1); 259 } 260 if (params.constructor !== Array) { 261 params = [params]; 262 } 263 $.each(params, function (i, n) { 264 source = source.replace(new RegExp("\\{" + i + "\\}", "g"), function () { 265 return n; 266 }); 267 }); 268 return source; 269 }; 270 271 $.extend($.validator, { 272 273 defaults: { 274 messages: {}, 275 groups: {}, 276 rules: {}, 277 errorClass: "error", 278 pendingClass: "pending", 279 validClass: "valid", 280 errorElement: "label", 281 focusCleanup: false, 282 focusInvalid: true, 283 errorContainer: $([]), 284 errorLabelContainer: $([]), 285 onsubmit: true, 286 ignore: ":hidden", 287 ignoreTitle: false, 288 onfocusin: function (element) { 289 this.lastActive = element; 290 291 // Hide error label and remove error class on focus if enabled 292 if (this.settings.focusCleanup) { 293 if (this.settings.unhighlight) { 294 this.settings.unhighlight.call(this, element, this.settings.errorClass, this.settings.validClass); 295 } 296 this.hideThese(this.errorsFor(element)); 297 } 298 }, 299 onfocusout: function (element) { 300 if (!this.checkable(element) && ( element.name in this.submitted || !this.optional(element) )) { 301 this.element(element); 302 } 303 }, 304 onkeyup: function (element, event) { 305 306 // Avoid revalidate the field when pressing one of the following keys 307 // Shift => 16 308 // Ctrl => 17 309 // Alt => 18 310 // Caps lock => 20 311 // End => 35 312 // Home => 36 313 // Left arrow => 37 314 // Up arrow => 38 315 // Right arrow => 39 316 // Down arrow => 40 317 // Insert => 45 318 // Num lock => 144 319 // AltGr key => 225 320 var excludedKeys = [ 321 16, 17, 18, 20, 35, 36, 37, 322 38, 39, 40, 45, 144, 225 323 ]; 324 325 if (event.which === 9 && this.elementValue(element) === "" || $.inArray(event.keyCode, excludedKeys) !== -1) { 326 return; 327 } else if (element.name in this.submitted || element.name in this.invalid) { 328 this.element(element); 329 } 330 }, 331 onclick: function (element) { 332 333 // Click on selects, radiobuttons and checkboxes 334 if (element.name in this.submitted) { 335 this.element(element); 336 337 // Or option elements, check parent select in that case 338 } else if (element.parentNode.name in this.submitted) { 339 this.element(element.parentNode); 340 } 341 }, 342 highlight: function (element, errorClass, validClass) { 343 if (element.type === "radio") { 344 this.findByName(element.name).addClass(errorClass).removeClass(validClass); 345 } else { 346 $(element).addClass(errorClass).removeClass(validClass); 347 } 348 }, 349 unhighlight: function (element, errorClass, validClass) { 350 if (element.type === "radio") { 351 this.findByName(element.name).removeClass(errorClass).addClass(validClass); 352 } else { 353 $(element).removeClass(errorClass).addClass(validClass); 354 } 355 } 356 }, 357 358 // https://jqueryvalidation.org/jQuery.validator.setDefaults/ 359 setDefaults: function (settings) { 360 $.extend($.validator.defaults, settings); 361 }, 362 363 messages: { 364 required: "This field is required.", 365 remote: "Please fix this field.", 366 email: "Please enter a valid email address.", 367 url: "Please enter a valid URL.", 368 date: "Please enter a valid date.", 369 dateISO: "Please enter a valid date (ISO).", 370 number: "Please enter a valid number.", 371 digits: "Please enter only digits.", 372 equalTo: "Please enter the same value again.", 373 maxlength: $.validator.format("Please enter no more than {0} characters."), 374 minlength: $.validator.format("Please enter at least {0} characters."), 375 rangelength: $.validator.format("Please enter a value between {0} and {1} characters long."), 376 range: $.validator.format("Please enter a value between {0} and {1}."), 377 max: $.validator.format("Please enter a value less than or equal to {0}."), 378 min: $.validator.format("Please enter a value greater than or equal to {0}."), 379 step: $.validator.format("Please enter a multiple of {0}.") 380 }, 381 382 autoCreateRanges: false, 383 384 prototype: { 385 386 init: function () { 387 this.labelContainer = $(this.settings.errorLabelContainer); 388 this.errorContext = this.labelContainer.length && this.labelContainer || $(this.currentForm); 389 this.containers = $(this.settings.errorContainer).add(this.settings.errorLabelContainer); 390 this.submitted = {}; 391 this.valueCache = {}; 392 this.pendingRequest = 0; 393 this.pending = {}; 394 this.invalid = {}; 395 this.reset(); 396 397 var groups = ( this.groups = {} ), 398 rules; 399 $.each(this.settings.groups, function (key, value) { 400 if (typeof value === "string") { 401 value = value.split(/\s/); 402 } 403 $.each(value, function (index, name) { 404 groups[name] = key; 405 }); 406 }); 407 rules = this.settings.rules; 408 $.each(rules, function (key, value) { 409 rules[key] = $.validator.normalizeRule(value); 410 }); 411 412 function delegate(event) { 413 414 // Set form expando on contenteditable 415 if (!this.form && this.hasAttribute("contenteditable")) { 416 this.form = $(this).closest("form")[0]; 417 this.name = $(this).attr("name"); 418 } 419
420 var validator = $.data(this.form, "validator"), 421 eventType = "on" + event.type.replace(/^validate/, ""), 422 settings = validator.settings; 423 if (settings[eventType] && !$(this).is(settings.ignore)) { 424 settings[eventType].call(validator, this, event); 425 } 426 } 427 428 $(this.currentForm) 429 .on("focusin.validate focusout.validate keyup.validate", 430 ":text, [type='password'], [type='file'], select, textarea, [type='number'], [type='search'], " + 431 "[type='tel'], [type='url'], [type='email'], [type='datetime'], [type='date'], [type='month'], " + 432 "[type='week'], [type='time'], [type='datetime-local'], [type='range'], [type='color'], " + 433 "[type='radio'], [type='checkbox'], [contenteditable], [type='button']", delegate) 434 435 // Support: Chrome, oldIE 436 // "select" is provided as event.target when clicking a option 437 .on("click.validate", "select, option, [type='radio'], [type='checkbox']", delegate); 438 439 if (this.settings.invalidHandler) { 440 $(this.currentForm).on("invalid-form.validate", this.settings.invalidHandler); 441 } 442 }, 443 444 // https://jqueryvalidation.org/Validator.form/ 445 form: function () { 446 this.checkForm(); 447 $.extend(this.submitted, this.errorMap); 448 this.invalid = $.extend({}, this.errorMap); 449 if (!this.valid()) { 450 $(this.currentForm).triggerHandler("invalid-form", [this]); 451 } 452 this.showErrors(); 453 return this.valid(); 454 }, 455 456 checkForm: function () { 457 this.prepareForm(); 458 for (var i = 0, elements = (this.currentElements = this.elements()); elements[i]; i++) { 459 if (this.findByName(elements[i].name).length != undefined && this.findByName(elements[i].name).length > 1) { 460 for (var cnt = 0; cnt < this.findByName(elements[i].name).length; cnt++) { 461 this.check(this.findByName(elements[i].name)[cnt]); 462 } 463 } else { 464 this.check(elements[i]); 465 } 466 } 467 return this.valid(); 468 }, 469 470 // https://jqueryvalidation.org/Validator.element/ 471 element: function (element) { 472 var cleanElement = this.clean(element), 473 checkElement = this.validationTargetFor(cleanElement), 474 v = this, 475 result = true, 476 rs, group; 477 478 if (checkElement === undefined) { 479 delete this.invalid[cleanElement.name]; 480 } else { 481 this.prepareElement(checkElement); 482 this.currentElements = $(checkElement); 483 484 // If this element is grouped, then validate all group elements already 485 // containing a value 486 group = this.groups[checkElement.name]; 487 if (group) { 488 $.each(this.groups, function (name, testgroup) { 489 if (testgroup === group && name !== checkElement.name) { 490 cleanElement = v.validationTargetFor(v.clean(v.findByName(name))); 491 if (cleanElement && cleanElement.name in v.invalid) { 492 v.currentElements.push(cleanElement); 493 result = v.check(cleanElement) && result; 494 } 495 } 496 }); 497 } 498 499 rs = this.check(checkElement) !== false; 500 result = result && rs; 501 if (rs) { 502 this.invalid[checkElement.name] = false;
vendor: 40,707 bytes, lines 503-1489
503 } else { 504 this.invalid[checkElement.name] = true; 505 } 506 507 if (!this.numberOfInvalids()) { 508 509 // Hide error containers on last error 510 this.toHide = this.toHide.add(this.containers); 511 } 512 this.showErrors(); 513 514 // Add aria-invalid status for screen readers 515 $(element).attr("aria-invalid", !rs); 516 } 517 518 return result; 519 }, 520 521 // https://jqueryvalidation.org/Validator.showErrors/ 522 showErrors: function (errors) { 523 if (errors) { 524 var validator = this; 525 526 // Add items to error list and map 527 $.extend(this.errorMap, errors); 528 this.errorList = $.map(this.errorMap, function (message, name) { 529 return { 530 message: message, 531 element: validator.findByName(name)[0] 532 }; 533 }); 534 535 // Remove items from success list 536 this.successList = $.grep(this.successList, function (element) { 537 return !( element.name in errors ); 538 }); 539 } 540 if (this.settings.showErrors) { 541 this.settings.showErrors.call(this, this.errorMap, this.errorList); 542 } else { 543 this.defaultShowErrors(); 544 } 545 }, 546 547 // https://jqueryvalidation.org/Validator.resetForm/ 548 resetForm: function () { 549 if ($.fn.resetForm) { 550 $(this.currentForm).resetForm(); 551 } 552 this.invalid = {}; 553 this.submitted = {}; 554 this.prepareForm(); 555 this.hideErrors(); 556 var elements = this.elements() 557 .removeData("previousValue") 558 .removeAttr("aria-invalid"); 559 560 this.resetElements(elements); 561 }, 562 563 resetElements: function (elements) { 564 var i; 565 566 if (this.settings.unhighlight) { 567 for (i = 0; elements[i]; i++) { 568 this.settings.unhighlight.call(this, elements[i], 569 this.settings.errorClass, ""); 570 this.findByName(elements[i].name).removeClass(this.settings.validClass); 571 } 572 } else { 573 elements 574 .removeClass(this.settings.errorClass) 575 .removeClass(this.settings.validClass); 576 } 577 }, 578 579 numberOfInvalids: function () { 580 return this.objectLength(this.invalid); 581 }, 582 583 objectLength: function (obj) { 584 /* jshint unused: false */ 585 var count = 0, 586 i; 587 for (i in obj) { 588 589 // This check allows counting elements with empty error 590 // message as invalid elements 591 if (obj[i] !== undefined && obj[i] !== null && obj[i] !== false) { 592 count++; 593 } 594 } 595 return count; 596 }, 597 598 hideErrors: function () { 599 this.hideThese(this.toHide); 600 }, 601 602 hideThese: function (errors) { 603 errors.not(this.containers).text(""); 604 this.addWrapper(errors).hide(); 605 }, 606 607 valid: function () { 608 return this.size() === 0; 609 }, 610 611 size: function () { 612 return this.errorList.length; 613 }, 614 615 focusInvalid: function () { 616 if (this.settings.focusInvalid) { 617 try { 618 $(this.findLastActive() || this.errorList.length && this.errorList[0].element || []) 619 .filter(":visible") 620 .focus() 621 622 // Manually trigger focusin event; without it, focusin handler isn't called, findLastActive won't have anything to find 623 .trigger("focusin"); 624 } catch (e) { 625 626 // Ignore IE throwing errors when focusing hidden elements 627 } 628 } 629 }, 630 631 findLastActive: function () { 632 var lastActive = this.lastActive; 633 return lastActive && $.grep(this.errorList, function (n) { 634 return n.element.name === lastActive.name; 635 }).length === 1 && lastActive; 636 }, 637 638 elements: function () { 639 var validator = this, 640 rulesCache = {}; 641 642 // Select all valid inputs inside the form (no submit or reset buttons) 643 return $(this.currentForm) 644 .find("input, select, textarea, [contenteditable]") 645 .not(":submit, :reset, :image, :disabled") 646 .not(this.settings.ignore) 647 .filter(function () { 648 var name = this.name || $(this).attr("name"); // For contenteditable 649 if (!name && validator.settings.debug && window.console) { 650 console.error("%o has no name assigned", this); 651 } 652 653 // Set form expando on contenteditable 654 if (this.hasAttribute("contenteditable")) { 655 this.form = $(this).closest("form")[0]; 656 this.name = name; 657 } 658 659 // Select only the first element for each name, and only those with rules specified 660 if (name in rulesCache || !validator.objectLength($(this).rules())) { 661 return false; 662 } 663 664 rulesCache[name] = true; 665 return true; 666 }); 667 }, 668 669 clean: function (selector) { 670 return $(selector)[0]; 671 }, 672 673 errors: function () { 674 var errorClass = this.settings.errorClass.split(" ").join("."); 675 return $(this.settings.errorElement + "." + errorClass, this.errorContext); 676 }, 677 678 resetInternals: function () { 679 this.successList = []; 680 this.errorList = []; 681 this.errorMap = {}; 682 this.toShow = $([]); 683 this.toHide = $([]); 684 }, 685 686 reset: function () { 687 this.resetInternals(); 688 this.currentElements = $([]); 689 }, 690 691 prepareForm: function () { 692 this.reset(); 693 this.toHide = this.errors().add(this.containers); 694 }, 695 696 prepareElement: function (element) { 697 this.reset(); 698 this.toHide = this.errorsFor(element); 699 }, 700 701 elementValue: function (element) { 702 var $element = $(element), 703 type = element.type, 704 val, idx; 705 706 if (type === "radio" || type === "checkbox") { 707 return this.findByName(element.name).filter(":checked").val(); 708 } else if (type === "number" && typeof element.validity !== "undefined") { 709 return element.validity.badInput ? "NaN" : $element.val(); 710 } 711 712 if (element.hasAttribute("contenteditable")) { 713 val = $element.text(); 714 } else { 715 val = $element.val(); 716 } 717 718 if (type === "file") { 719 720 // Modern browser (chrome & safari) 721 if (val.substr(0, 12) === "C:\\fakepath\\") { 722 return val.substr(12); 723 } 724 725 // Legacy browsers 726 // Unix-based path 727 idx = val.lastIndexOf("/"); 728 if (idx >= 0) { 729 return val.substr(idx + 1); 730 } 731 732 // Windows-based path 733 idx = val.lastIndexOf("\\"); 734 if (idx >= 0) { 735 return val.substr(idx + 1); 736 } 737 738 // Just the file name 739 return val; 740 } 741 742 if (typeof val === "string") { 743 return val.replace(/\r/g, ""); 744 } 745 return val; 746 }, 747 748 check: function (element) { 749 element = this.validationTargetFor(this.clean(element)); 750 751 var rules = $(element).rules(), 752 rulesCount = $.map(rules, function (n, i) { 753 return i; 754 }).length, 755 dependencyMismatch = false, 756 val = this.elementValue(element), 757 result, method, rule, normalizer; 758 759 // Prioritize the local normalizer defined for this element over the global one 760 // if the former exists, otherwise user the global one in case it exists. 761 if (typeof rules.normalizer === "function") { 762 normalizer = rules.normalizer; 763 } else if (typeof this.settings.normalizer === "function") { 764 normalizer = this.settings.normalizer; 765 } 766 767 // If normalizer is defined, then call it to retreive the changed value instead 768 // of using the real one. 769 // Note that `this` in the normalizer is `element`. 770 if (normalizer) { 771 val = normalizer.call(element, val); 772 773 if (typeof val !== "string") { 774 throw new TypeError("The normalizer should return a string value."); 775 } 776 777 // Delete the normalizer from rules to avoid treating it as a pre-defined method. 778 delete rules.normalizer; 779 } 780 781 for (method in rules) { 782 rule = {method: method, parameters: rules[method]}; 783 try { 784 result = $.validator.methods[method].call(this, val, element, rule.parameters); 785 786 // If a method indicates that the field is optional and therefore valid, 787 // don't mark it as valid when there are no other rules 788 if (result === "dependency-mismatch" && rulesCount === 1) { 789 dependencyMismatch = true; 790 continue; 791 } 792 dependencyMismatch = false; 793 794 if (result === "pending") { 795 this.toHide = this.toHide.not(this.errorsFor(element)); 796 return; 797 } 798 799 if (!result) { 800 this.formatAndAdd(element, rule); 801 return false; 802 } 803 } catch (e) { 804 if (this.settings.debug && window.console) { 805 console.log("Exception occurred when checking element " + element.id + ", check the '" + rule.method + "' method.", e); 806 } 807 if (e instanceof TypeError) { 808 e.message += ". Exception occurred when checking element " + element.id + ", check the '" + rule.method + "' method."; 809 } 810 811 throw e; 812 } 813 } 814 if (dependencyMismatch) { 815 return; 816 } 817 if (this.objectLength(rules)) { 818 this.successList.push(element); 819 } 820 return true; 821 }, 822 823 // Return the custom message for the given element and validation method 824 // specified in the element's HTML5 data attribute 825 // return the generic message if present and no method specific message is present 826 customDataMessage: function (element, method) { 827 return $(element).data("msg" + method.charAt(0).toUpperCase() + 828 method.substring(1).toLowerCase()) || $(element).data("msg"); 829 }, 830 831 // Return the custom message for the given element name and validation method 832 customMessage: function (name, method) { 833 var m = this.settings.messages[name]; 834 return m && ( m.constructor === String ? m : m[method] ); 835 }, 836 837 // Return the first defined argument, allowing empty strings 838 findDefined: function () { 839 for (var i = 0; i < arguments.length; i++) { 840 if (arguments[i] !== undefined) { 841 return arguments[i]; 842 } 843 } 844 return undefined; 845 }, 846 847 // The second parameter 'rule' used to be a string, and extended to an object literal 848 // of the following form: 849 // rule = { 850 // method: "method name", 851 // parameters: "the given method parameters" 852 // } 853 // 854 // The old behavior still supported, kept to maintain backward compatibility with 855 // old code, and will be removed in the next major release. 856 defaultMessage: function (element, rule) { 857 if (typeof rule === "string") { 858 rule = {method: rule}; 859 } 860 861 var message = this.findDefined( 862 this.customMessage(element.name, rule.method), 863 this.customDataMessage(element, rule.method), 864 865 // 'title' is never undefined, so handle empty string as undefined 866 !this.settings.ignoreTitle && element.title || undefined, 867 $.validator.messages[rule.method], 868 "<strong>Warning: No message defined for " + element.name + "</strong>" 869 ), 870 theregex = /\$?\{(\d+)\}/g; 871 if (typeof message === "function") { 872 message = message.call(this, rule.parameters, element); 873 } else if (theregex.test(message)) { 874 message = $.validator.format(message.replace(theregex, "{$1}"), rule.parameters); 875 } 876 877 return message; 878 }, 879 880 formatAndAdd: function (element, rule) { 881 var message = this.defaultMessage(element, rule); 882 883 this.errorList.push({ 884 message: message, 885 element: element, 886 method: rule.method 887 }); 888 889 this.errorMap[element.name] = message; 890 this.submitted[element.name] = message; 891 }, 892 893 addWrapper: function (toToggle) { 894 if (this.settings.wrapper) { 895 toToggle = toToggle.add(toToggle.parent(this.settings.wrapper)); 896 } 897 return toToggle; 898 }, 899 900 defaultShowErrors: function () { 901 var i, elements, error; 902 for (i = 0; this.errorList[i]; i++) { 903 error = this.errorList[i]; 904 if (this.settings.highlight) { 905 this.settings.highlight.call(this, error.element, this.settings.errorClass, this.settings.validClass); 906 } 907 this.showLabel(error.element, error.message); 908 } 909 if (this.errorList.length) { 910 this.toShow = this.toShow.add(this.containers); 911 } 912 if (this.settings.success) { 913 for (i = 0; this.successList[i]; i++) { 914 this.showLabel(this.successList[i]); 915 } 916 } 917 if (this.settings.unhighlight) { 918 for (i = 0, elements = this.validElements(); elements[i]; i++) { 919 this.settings.unhighlight.call(this, elements[i], this.settings.errorClass, this.settings.validClass); 920 } 921 } 922 this.toHide = this.toHide.not(this.toShow); 923 this.hideErrors(); 924 this.addWrapper(this.toShow).show(); 925 }, 926 927 validElements: function () { 928 return this.currentElements.not(this.invalidElements()); 929 }, 930 931 invalidElements: function () { 932 return $(this.errorList).map(function () { 933 return this.element; 934 }); 935 }, 936 937 showLabel: function (element, message) { 938 var place, group, errorID, v, 939 error = this.errorsFor(element), 940 elementID = this.idOrName(element), 941 describedBy = $(element).attr("aria-describedby"); 942 943 if (error.length) { 944 945 // Refresh error/success class 946 error.removeClass(this.settings.validClass).addClass(this.settings.errorClass); 947 948 // Replace message on existing label 949 error.html(message); 950 } else { 951 952 // Create error element 953 error = $("<" + this.settings.errorElement + ">") 954 .attr("id", elementID + "-error") 955 .addClass(this.settings.errorClass) 956 .html(message || ""); 957 958 // Maintain reference to the element to be placed into the DOM 959 place = error; 960 if (this.settings.wrapper) { 961 962 // Make sure the element is visible, even in IE 963 // actually showing the wrapped element is handled elsewhere 964 place = error.hide().show().wrap("<" + this.settings.wrapper + "/>").parent(); 965 } 966 if (this.labelContainer.length) { 967 this.labelContainer.append(place); 968 } else if (this.settings.errorPlacement) { 969 this.settings.errorPlacement.call(this, place, $(element)); 970 } else { 971 place.insertAfter(element); 972 } 973 974 // Link error back to the element 975 if (error.is("label")) { 976 977 // If the error is a label, then associate using 'for' 978 error.attr("for", elementID); 979 980 // If the element is not a child of an associated label, then it's necessary 981 // to explicitly apply aria-describedby 982 } else if (error.parents("label[for='" + this.escapeCssMeta(elementID) + "']").length === 0) { 983 errorID = error.attr("id"); 984 985 // Respect existing non-error aria-describedby 986 if (!describedBy) { 987 describedBy = errorID; 988 } else if (!describedBy.match(new RegExp("\\b" + this.escapeCssMeta(errorID) + "\\b"))) { 989 990 // Add to end of list if not already present 991 describedBy += " " + errorID; 992 } 993 $(element).attr("aria-describedby", describedBy); 994 995 // If this element is grouped, then assign to all elements in the same group 996 group = this.groups[element.name]; 997 if (group) { 998 v = this; 999 $.each(v.groups, function (name, testgroup) { 1000 if (testgroup === group) { 1001 $("[name='" + v.escapeCssMeta(name) + "']", v.currentForm) 1002 .attr("aria-describedby", error.attr("id")); 1003 } 1004 }); 1005 } 1006 } 1007 } 1008 if (!message && this.settings.success) { 1009 error.text(""); 1010 if (typeof this.settings.success === "string") { 1011 error.addClass(this.settings.success); 1012 } else { 1013 this.settings.success(error, element); 1014 } 1015 } 1016 this.toShow = this.toShow.add(error); 1017 }, 1018 1019 errorsFor: function (element) { 1020 var name = this.escapeCssMeta(this.idOrName(element)), 1021 describer = $(element).attr("aria-describedby"), 1022 selector = "label[for='" + name + "'], label[for='" + name + "'] *"; 1023 1024 // 'aria-describedby' should directly reference the error element 1025 if (describer) { 1026 selector = selector + ", #" + this.escapeCssMeta(describer) 1027 .replace(/\s+/g, ", #"); 1028 } 1029 1030 return this 1031 .errors() 1032 .filter(selector); 1033 }, 1034 1035 // See https://api.jquery.com/category/selectors/, for CSS 1036 // meta-characters that should be escaped in order to be used with JQuery 1037 // as a literal part of a name/id or any selector. 1038 escapeCssMeta: function (string) { 1039 return string.replace(/([\\!"#$%&'()*+,./:;<=>?@\[\]^`{|}~])/g, "\\$1"); 1040 }, 1041 1042 idOrName: function (element) { 1043 return this.groups[element.name] || ( this.checkable(element) ? element.name : element.id || element.name ); 1044 }, 1045 1046 validationTargetFor: function (element) { 1047 1048 // If radio/checkbox, validate first element in group instead 1049 if (this.checkable(element)) { 1050 element = this.findByName(element.name); 1051 } 1052 1053 // Always apply ignore filter 1054 return $(element).not(this.settings.ignore)[0]; 1055 }, 1056 1057 checkable: function (element) { 1058 return ( /radio|checkbox/i ).test(element.type); 1059 }, 1060 1061 findByName: function (name) { 1062 return $(this.currentForm).find("[name='" + this.escapeCssMeta(name) + "']"); 1063 }, 1064 1065 getLength: function (value, element) { 1066 switch (element.nodeName.toLowerCase()) { 1067 case "select": 1068 return $("option:selected", element).length; 1069 case "input": 1070 if (this.checkable(element)) { 1071 return this.findByName(element.name).filter(":checked").length; 1072 } 1073 } 1074 return value.length; 1075 }, 1076 1077 depend: function (param, element) { 1078 return this.dependTypes[typeof param] ? this.dependTypes[typeof param](param, element) : true; 1079 }, 1080 1081 dependTypes: { 1082 "boolean": function (param) { 1083 return param; 1084 }, 1085 "string": function (param, element) { 1086 return !!$(param, element.form).length; 1087 }, 1088 "function": function (param, element) { 1089 return param(element); 1090 } 1091 }, 1092 1093 optional: function (element) { 1094 var val = this.elementValue(element); 1095 return !$.validator.methods.required.call(this, val, element) && "dependency-mismatch"; 1096 }, 1097 1098 startRequest: function (element) { 1099 if (!this.pending[element.name]) { 1100 this.pendingRequest++; 1101 $(element).addClass(this.settings.pendingClass); 1102 this.pending[element.name] = true; 1103 } 1104 }, 1105 1106 stopRequest: function (element, valid) { 1107 this.pendingRequest--; 1108 1109 // Sometimes synchronization fails, make sure pendingRequest is never < 0 1110 if (this.pendingRequest < 0) { 1111 this.pendingRequest = 0; 1112 } 1113 delete this.pending[element.name]; 1114 $(element).removeClass(this.settings.pendingClass); 1115 if (valid && this.pendingRequest === 0 && this.formSubmitted && this.form()) { 1116 $(this.currentForm).submit(); 1117 1118 // Remove the hidden input that was used as a replacement for the 1119 // missing submit button. The hidden input is added by `handle()` 1120 // to ensure that the value of the used submit button is passed on 1121 // for scripted submits triggered by this method 1122 if (this.submitButton) { 1123 $("input:hidden[name='" + this.submitButton.name + "']", this.currentForm).remove(); 1124 } 1125 1126 this.formSubmitted = false; 1127 } else if (!valid && this.pendingRequest === 0 && this.formSubmitted) { 1128 $(this.currentForm).triggerHandler("invalid-form", [this]); 1129 this.formSubmitted = false; 1130 } 1131 }, 1132 1133 previousValue: function (element, method) { 1134 method = typeof method === "string" && method || "remote"; 1135 1136 return $.data(element, "previousValue") || $.data(element, "previousValue", { 1137 old: null, 1138 valid: true, 1139 message: this.defaultMessage(element, {method: method}) 1140 }); 1141 }, 1142 1143 // Cleans up all forms and elements, removes validator-specific events 1144 destroy: function () { 1145 this.resetForm(); 1146 1147 $(this.currentForm) 1148 .off(".validate") 1149 .removeData("validator") 1150 .find(".validate-equalTo-blur") 1151 .off(".validate-equalTo") 1152 .removeClass("validate-equalTo-blur"); 1153 } 1154 1155 }, 1156 1157 classRuleSettings: { 1158 required: {required: true}, 1159 email: {email: true}, 1160 url: {url: true}, 1161 date: {date: true}, 1162 dateISO: {dateISO: true}, 1163 number: {number: true}, 1164 digits: {digits: true}, 1165 creditcard: {creditcard: true} 1166 }, 1167 1168 addClassRules: function (className, rules) { 1169 if (className.constructor === String) { 1170 this.classRuleSettings[className] = rules; 1171 } else { 1172 $.extend(this.classRuleSettings, className); 1173 } 1174 }, 1175 1176 classRules: function (element) { 1177 var rules = {}, 1178 classes = $(element).attr("class"); 1179 1180 if (classes) { 1181 $.each(classes.split(" "), function () { 1182 if (this in $.validator.classRuleSettings) { 1183 $.extend(rules, $.validator.classRuleSettings[this]); 1184 } 1185 }); 1186 } 1187 return rules; 1188 }, 1189 1190 normalizeAttributeRule: function (rules, type, method, value) { 1191 1192 // Convert the value to a number for number inputs, and for text for backwards compability 1193 // allows type="date" and others to be compared as strings 1194 if (/min|max|step/.test(method) && ( type === null || /number|range|text/.test(type) )) { 1195 value = Number(value); 1196 1197 // Support Opera Mini, which returns NaN for undefined minlength 1198 if (isNaN(value)) { 1199 value = undefined; 1200 } 1201 } 1202 1203 if (value || value === 0) { 1204 rules[method] = value; 1205 } else if (type === method && type !== "range") { 1206 1207 // Exception: the jquery validate 'range' method 1208 // does not test for the html5 'range' type 1209 rules[method] = true; 1210 } 1211 }, 1212 1213 attributeRules: function (element) { 1214 var rules = {}, 1215 $element = $(element), 1216 type = element.getAttribute("type"), 1217 method, value; 1218 1219 for (method in $.validator.methods) { 1220 1221 // Support for <input required> in both html5 and older browsers 1222 if (method === "required") { 1223 value = element.getAttribute(method); 1224 1225 // Some browsers return an empty string for the required attribute 1226 // and non-HTML5 browsers might have required="" markup 1227 if (value === "") { 1228 value = true; 1229 } 1230 1231 // Force non-HTML5 browsers to return bool 1232 value = !!value; 1233 } else { 1234 value = $element.attr(method); 1235 } 1236 1237 this.normalizeAttributeRule(rules, type, method, value); 1238 } 1239 1240 // 'maxlength' may be returned as -1, 2147483647 ( IE ) and 524288 ( safari ) for text inputs 1241 if (rules.maxlength && /-1|2147483647|524288/.test(rules.maxlength)) { 1242 delete rules.maxlength; 1243 } 1244 1245 return rules; 1246 }, 1247 1248 dataRules: function (element) { 1249 var rules = {}, 1250 $element = $(element), 1251 type = element.getAttribute("type"), 1252 method, value; 1253 1254 for (method in $.validator.methods) { 1255 value = $element.data("rule" + method.charAt(0).toUpperCase() + method.substring(1).toLowerCase()); 1256 this.normalizeAttributeRule(rules, type, method, value); 1257 } 1258 return rules; 1259 }, 1260 1261 staticRules: function (element) { 1262 var rules = {}, 1263 validator = $.data(element.form, "validator"); 1264 1265 if (validator.settings.rules) { 1266 rules = $.validator.normalizeRule(validator.settings.rules[element.name]) || {}; 1267 } 1268 return rules; 1269 }, 1270 1271 normalizeRules: function (rules, element) { 1272 1273 // Handle dependency check 1274 $.each(rules, function (prop, val) { 1275 1276 // Ignore rule when param is explicitly false, eg. required:false 1277 if (val === false) { 1278 delete rules[prop]; 1279 return; 1280 } 1281 if (val.param || val.depends) { 1282 var keepRule = true; 1283 switch (typeof val.depends) { 1284 case "string": 1285 keepRule = !!$(val.depends, element.form).length; 1286 break; 1287 case "function": 1288 keepRule = val.depends.call(element, element); 1289 break; 1290 } 1291 if (keepRule) { 1292 rules[prop] = val.param !== undefined ? val.param : true; 1293 } else { 1294 $.data(element.form, "validator").resetElements($(element)); 1295 delete rules[prop]; 1296 } 1297 } 1298 }); 1299 1300 // Evaluate parameters 1301 $.each(rules, function (rule, parameter) { 1302 rules[rule] = $.isFunction(parameter) && rule !== "normalizer" ? parameter(element) : parameter; 1303 }); 1304 1305 // Clean number parameters 1306 $.each(["minlength", "maxlength"], function () { 1307 if (rules[this]) { 1308 rules[this] = Number(rules[this]); 1309 } 1310 }); 1311 $.each(["rangelength", "range"], function () { 1312 var parts; 1313 if (rules[this]) { 1314 if ($.isArray(rules[this])) { 1315 rules[this] = [Number(rules[this][0]), Number(rules[this][1])]; 1316 } else if (typeof rules[this] === "string") { 1317 parts = rules[this].replace(/[\[\]]/g, "").split(/[\s,]+/); 1318 rules[this] = [Number(parts[0]), Number(parts[1])]; 1319 } 1320 } 1321 }); 1322 1323 if ($.validator.autoCreateRanges) { 1324 1325 // Auto-create ranges 1326 if (rules.min != null && rules.max != null) { 1327 rules.range = [rules.min, rules.max]; 1328 delete rules.min; 1329 delete rules.max; 1330 } 1331 if (rules.minlength != null && rules.maxlength != null) { 1332 rules.rangelength = [rules.minlength, rules.maxlength]; 1333 delete rules.minlength; 1334 delete rules.maxlength; 1335 } 1336 } 1337 1338 return rules; 1339 }, 1340 1341 // Converts a simple string to a {string: true} rule, e.g., "required" to {required:true} 1342 normalizeRule: function (data) { 1343 if (typeof data === "string") { 1344 var transformed = {}; 1345 $.each(data.split(/\s/), function () { 1346 transformed[this] = true; 1347 }); 1348 data = transformed; 1349 } 1350 return data; 1351 }, 1352 1353 // https://jqueryvalidation.org/jQuery.validator.addMethod/ 1354 addMethod: function (name, method, message) { 1355 $.validator.methods[name] = method; 1356 $.validator.messages[name] = message !== undefined ? message : $.validator.messages[name]; 1357 if (method.length < 3) { 1358 $.validator.addClassRules(name, $.validator.normalizeRule(name)); 1359 } 1360 }, 1361 1362 // https://jqueryvalidation.org/jQuery.validator.methods/ 1363 methods: { 1364 1365 // https://jqueryvalidation.org/required-method/ 1366 required: function (value, element, param) { 1367 1368 // Check if dependency is met 1369 if (!this.depend(param, element)) { 1370 return "dependency-mismatch"; 1371 } 1372 if (element.nodeName.toLowerCase() === "select") { 1373 1374 // Could be an array for select-multiple or a string, both are fine this way 1375 var val = $(element).val(); 1376 return val && val.length > 0; 1377 } 1378 if (this.checkable(element)) { 1379 return this.getLength(value, element) > 0; 1380 } 1381 return value.length > 0; 1382 }, 1383 1384 // https://jqueryvalidation.org/email-method/ 1385 email: function (value, element) { 1386 1387 // From https://html.spec.whatwg.org/multipage/forms.html#valid-e-mail-address 1388 // Retrieved 2014-01-14 1389 // If you have a problem with this implementation, report a bug against the above spec 1390 // Or use custom methods to implement your own email validation 1391 return this.optional(element) || /^[a-zA-Z0-9.!#$%&'*+\/=?^_`{|}~-]+@[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?(?:\.[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?)*$/.test(value); 1392 }, 1393 1394 // https://jqueryvalidation.org/url-method/ 1395 url: function (value, element) { 1396 1397 // Copyright (c) 2010-2013 Diego Perini, MIT licensed 1398 // https://gist.github.com/dperini/729294 1399 // see also https://mathiasbynens.be/demo/url-regex 1400 // modified to allow protocol-relative URLs 1401 return this.optional(element) || /^(?:(?:(?:https?|ftp):)?\/\/)(?:\S+(?::\S*)?@)?(?:(?!(?:10|127)(?:\.\d{1,3}){3})(?!(?:169\.254|192\.168)(?:\.\d{1,3}){2})(?!172\.(?:1[6-9]|2\d|3[0-1])(?:\.\d{1,3}){2})(?:[1-9]\d?|1\d\d|2[01]\d|22[0-3])(?:\.(?:1?\d{1,2}|2[0-4]\d|25[0-5])){2}(?:\.(?:[1-9]\d?|1\d\d|2[0-4]\d|25[0-4]))|(?:(?:[a-z\u00a1-\uffff0-9]-*)*[a-z\u00a1-\uffff0-9]+)(?:\.(?:[a-z\u00a1-\uffff0-9]-*)*[a-z\u00a1-\uffff0-9]+)*(?:\.(?:[a-z\u00a1-\uffff]{2,})).?)(?::\d{2,5})?(?:[/?#]\S*)?$/i.test(value); 1402 }, 1403 1404 // https://jqueryvalidation.org/date-method/ 1405 date: function (value, element) { 1406 return this.optional(element) || !/Invalid|NaN/.test(new Date(value).toString()); 1407 }, 1408 1409 // https://jqueryvalidation.org/dateISO-method/ 1410 dateISO: function (value, element) { 1411 return this.optional(element) || /^\d{4}[\/\-](0?[1-9]|1[012])[\/\-](0?[1-9]|[12][0-9]|3[01])$/.test(value); 1412 }, 1413 1414 // https://jqueryvalidation.org/number-method/ 1415 number: function (value, element) { 1416 return this.optional(element) || /^(?:-?\d+|-?\d{1,3}(?:,\d{3})+)?(?:\.\d+)?$/.test(value); 1417 }, 1418 1419 // https://jqueryvalidation.org/digits-method/ 1420 digits: function (value, element) { 1421 return this.optional(element) || /^\d+$/.test(value); 1422 }, 1423 1424 // https://jqueryvalidation.org/minlength-method/ 1425 minlength: function (value, element, param) { 1426 var length = $.isArray(value) ? value.length : this.getLength(value, element); 1427 return this.optional(element) || length >= param; 1428 }, 1429 1430 // https://jqueryvalidation.org/maxlength-method/ 1431 maxlength: function (value, element, param) { 1432 var length = $.isArray(value) ? value.length : this.getLength(value, element); 1433 return this.optional(element) || length <= param; 1434 }, 1435 1436 // https://jqueryvalidation.org/rangelength-method/ 1437 rangelength: function (value, element, param) { 1438 var length = $.isArray(value) ? value.length : this.getLength(value, element); 1439 return this.optional(element) || ( length >= param[0] && length <= param[1] ); 1440 }, 1441 1442 // https://jqueryvalidation.org/min-method/ 1443 min: function (value, element, param) { 1444 return this.optional(element) || value >= param; 1445 }, 1446 1447 // https://jqueryvalidation.org/max-method/ 1448 max: function (value, element, param) { 1449 return this.optional(element) || value <= param; 1450 }, 1451 1452 // https://jqueryvalidation.org/range-method/ 1453 range: function (value, element, param) { 1454 return this.optional(element) || ( value >= param[0] && value <= param[1] ); 1455 }, 1456 1457 // https://jqueryvalidation.org/step-method/ 1458 step: function (value, element, param) { 1459 var type = $(element).attr("type"), 1460 errorMessage = "Step attribute on input type " + type + " is not supported.", 1461 supportedTypes = ["text", "number", "range"], 1462 re = new RegExp("\\b" + type + "\\b"), 1463 notSupported = type && !re.test(supportedTypes.join()), 1464 decimalPlaces = function (num) { 1465 var match = ( "" + num ).match(/(?:\.(\d+))?$/); 1466 if (!match) { 1467 return 0; 1468 } 1469 1470 // Number of digits right of decimal point. 1471 return match[1] ? match[1].length : 0; 1472 }, 1473 toInt = function (num) { 1474 return Math.round(num * Math.pow(10, decimals)); 1475 }, 1476 valid = true, 1477 decimals; 1478 1479 // Works only for text, number and range input types 1480 // TODO find a way to support input types date, datetime, datetime-local, month, time and week 1481 if (notSupported) { 1482 throw new Error(errorMessage); 1483 } 1484 1485 decimals = decimalPlaces(param); 1486 1487 // Value can't have too many decimals 1488 if (decimalPlaces(value) > decimals || toInt(value) % toInt(param) !== 0) { 1489 valid = false;
1490 } 1491 1492 return this.optional(element) || valid; 1493 }, 1494 1495 // https://jqueryvalidation.org/equalTo-method/ 1496 equalTo: function (value, element, param) { 1497 1498 // Bind to the blur event of the target in order to revalidate whenever the target field is updated 1499 var target = $(param); 1500 if (this.settings.onfocusout && target.not(".validate-equalTo-blur").length) { 1501 target.addClass("validate-equalTo-blur").on("blur.validate-equalTo", function () { 1502 $(element).valid(); 1503 }); 1504 } 1505 return value === target.val(); 1506 }, 1507 1508 // https://jqueryvalidation.org/remote-method/ 1509 remote: function (value, element, param, method) { 1510 if (this.optional(element)) { 1511 return "dependency-mismatch"; 1512 } 1513 1514 method = typeof method === "string" && method || "remote"; 1515 1516 var previous = this.previousValue(element, method), 1517 validator, data, optionDataString; 1518 1519 if (!this.settings.messages[element.name]) { 1520 this.settings.messages[element.name] = {}; 1521 } 1522 previous.originalMessage = previous.originalMessage || this.settings.messages[element.name][method]; 1523 this.settings.messages[element.name][method] = previous.message; 1524 1525 param = typeof param === "string" && {url: param} || param; 1526 optionDataString = $.param($.extend({data: value}, param.data)); 1527 if (previous.old === optionDataString) { 1528 return previous.valid; 1529 } 1530 1531 previous.old = optionDataString; 1532 validator = this; 1533 this.startRequest(element); 1534 data = {}; 1535 data[element.name] = value; 1536 $.ajax($.extend(true, { 1537 mode: "abort", 1538 port: "validate" + element.name, 1539 dataType: "json", 1540 data: data, 1541 context: validator.currentForm, 1542 success: function (response) { 1543 var valid = response === true || response === "true", 1544 errors, message, submitted; 1545 1546 validator.settings.messages[element.name][method] = previous.originalMessage; 1547 if (valid) { 1548 submitted = validator.formSubmitted; 1549 validator.resetInternals(); 1550 validator.toHide = validator.errorsFor(element); 1551 validator.formSubmitted = submitted; 1552 validator.successList.push(element); 1553 validator.invalid[element.name] = false; 1554 validator.showErrors(); 1555 } else { 1556 errors = {}; 1557 message = response || validator.defaultMessage(element, { 1558 method: method, 1559 parameters: value 1560 }); 1561 errors[element.name] = previous.message = message; 1562 validator.invalid[element.name] = true; 1563 validator.showErrors(errors); 1564 } 1565 previous.valid = valid; 1566 validator.stopRequest(element, valid); 1567 } 1568 }, param)); 1569 return "pending"; 1570 }, 1571 1572 filesize: function (value, element, size) { 1573 return this.optional(element) || (element.files[0].size <= size) 1574 }, 1575 1576 noSpace: function (value, element) { 1577 return this.optional(element) || /^[^\s]*$/.test(value); 1578 }, 1579 1580 regex: function (value, element, regexp) { 1581 if (regexp.constructor != RegExp) 1582 regexp = new RegExp(regexp); 1583 else if (regexp.global) 1584 regexp.lastIndex = 0; 1585 return this.optional(element) || regexp.test(value); 1586 }, 1587 1588 regex1: function (value, element, regexp) { 1589 if (regexp.constructor != RegExp) 1590 regexp = new RegExp(regexp); 1591 else if (regexp.global) 1592 regexp.lastIndex = 0; 1593 return this.optional(element) || regexp.test(value); 1594 }, 1595 1596 // extension: function (value, element, param) { 1597 // param = typeof param === "string" ? param.replace(/,/g, '|') : "png|jpe?g|gif"; 1598 // return this.optional(element) || value.match(new RegExp(".(" + param + ")$", "i")); 1599 // } 1600 } 1601 1602 }); 1603 1604// Ajax mode: abort 1605// usage: $.ajax({ mode: "abort"[, port: "uniqueport"]}); 1606// if mode:"abort" is used, the previous request on that port (port can be undefined) is aborted via XMLHttpRequest.abort() 1607 1608 var pendingRequests = {}, 1609 ajax; 1610 1611// Use a prefilter if available (1.5+) 1612 if ($.ajaxPrefilter) { 1613 $.ajaxPrefilter(function (settings, _, xhr) { 1614 var port = settings.port; 1615 if (settings.mode === "abort") { 1616 if (pendingRequests[port]) { 1617 pendingRequests[port].abort(); 1618 } 1619 pendingRequests[port] = xhr; 1620 } 1621 }); 1622 } else { 1623 1624 // Proxy ajax 1625 ajax = $.ajax; 1626 $.ajax = function (settings) { 1627 var mode = ( "mode" in settings ? settings : $.ajaxSettings ).mode, 1628 port = ( "port" in settings ? settings : $.ajaxSettings ).port; 1629 if (mode === "abort") { 1630 if (pendingRequests[port]) { 1631 pendingRequests[port].abort(); 1632 } 1633 pendingRequests[port] = ajax.apply(this, arguments); 1634 return pendingRequests[port]; 1635 } 1636 return ajax.apply(this, arguments); 1637 }; 1638 } 1639 return $; 1640}));
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.