1/*! 2* jQuery Password Strength plugin for Twitter Bootstrap 3* Version: 2.1.1 4* 5* Copyright (c) 2008-2013 Tane Piper 6* Copyright (c) 2013 Alejandro Blanco 7* Dual licensed under the MIT and GPL licenses. 8*/ 9 10(function (jQuery) { 11// Source: src/i18n.js 12 13 14 15 16var i18n = {}; 17 18(function (i18n, i18next) { 19 'use strict'; 20 21 i18n.fallback = { 22 "wordMinLength": "Your password is too short", 23 "wordMaxLength": "Your password is too long", 24 "wordInvalidChar": "Your password contains an invalid character", 25 "wordNotEmail": "Do not use your email as your password", 26 "wordSimilarToUsername": "Your password cannot contain your username", 27 "wordTwoCharacterClasses": "Use different character classes", 28 "wordRepetitions": "Too many repetitions", 29 "wordSequences": "Your password contains sequences", 30 "errorList": "Errors:", 31 "veryWeak": "Very Weak", 32 "weak": "Weak", 33 "normal": "Normal", 34 "medium": "Medium", 35 "strong": "Strong", 36 "veryStrong": "Very Strong" 37 }; 38 39 i18n.t = function (key) { 40 var result = ''; 41 42 // Try to use i18next.com 43 if (i18next) { 44 result = i18next.t(key); 45 } else { 46 // Fallback to english 47 result = i18n.fallback[key]; 48 } 49 50 return result === key ? '' : result; 51 }; 52}(i18n, window.i18next)); 53 54// Source: src/rules.js 55 56 57 58 59var rulesEngine = {}; 60 61try { 62 if (!jQuery && module && module.exports) { 63 var jQuery = require("jquery"), 64 jsdom = require("jsdom").jsdom; 65 jQuery = jQuery(jsdom().defaultView); 66 } 67} catch (ignore) {} 68 69(function ($, rulesEngine) { 70 "use strict"; 71 var validation = {}; 72 73 rulesEngine.forbiddenSequences = [ 74 "0123456789", "abcdefghijklmnopqrstuvwxyz", "qwertyuiop", "asdfghjkl", 75 "zxcvbnm", "!@#$%^&*()_+" 76 ]; 77 78 validation.wordNotEmail = function (options, word, score) { 79 if (word.match(/^([\w\!\#$\%\&\'\*\+\-\/\=\?\^\`{\|\}\~]+\.)*[\w\!\#$\%\&\'\*\+\-\/\=\?\^\`{\|\}\~]+@((((([a-z0-9]{1}[a-z0-9\-]{0,62}[a-z0-9]{1})|[a-z])\.)+[a-z]{2,6})|(\d{1,3}\.){3}\d{1,3}(\:\d{1,5})?)$/i)) { 80 return score; 81 } 82 return 0; 83 }; 84 85 validation.wordMinLength = function (options, word, score) { 86 var wordlen = word.length, 87 lenScore = Math.pow(wordlen, options.rules.raisePower); 88 if (wordlen < options.common.minChar) { 89 lenScore = (lenScore + score); 90 } 91 return lenScore; 92 }; 93 94 validation.wordMaxLength = function (options, word, score) { 95 var wordlen = word.length, 96 lenScore = Math.pow(wordlen, options.rules.raisePower); 97 if (wordlen > options.common.maxChar) { 98 return score; 99 } 100 return lenScore; 101 }; 102 103 validation.wordInvalidChar = function (options, word, score) { 104 if (word.match(/[\s,',"]/)) { 105 return score; 106 } 107 return 0; 108 }; 109 110 validation.wordLengthStaticScore = function (options, word, score) { 111 return word.length < options.common.minChar ? 0 : score; 112 }; 113 114 validation.wordSimilarToUsername = function (options, word, score) { 115 var username = $(options.common.usernameField).val(); 116 if (username && word.toLowerCase().match(username.replace(/[\-\[\]\/\{\}\(\)\*\+\=\?\:\.\\\^\$\|\!\,]/g, "\\$&").toLowerCase())) { 117 return score; 118 } 119 return 0; 120 }; 121 122 validation.wordTwoCharacterClasses = function (options, word, score) { 123 if (word.match(/([a-z].*[A-Z])|([A-Z].*[a-z])/) || 124 (word.match(/([a-zA-Z])/) && word.match(/([0-9])/)) || 125 (word.match(/(.[!,@,#,$,%,\^,&,*,?,_,~])/) && word.match(/[a-zA-Z0-9_]/))) { 126 return score; 127 } 128 return 0; 129 }; 130 131 validation.wordRepetitions = function (options, word, score) { 132 if (word.match(/(.)\1\1/)) { return score; } 133 return 0; 134 }; 135 136 validation.wordSequences = function (options, word, score) { 137 var found = false, 138 j; 139 if (word.length > 2) { 140 $.each(rulesEngine.forbiddenSequences, function (idx, seq) { 141 if (found) { return; } 142 var sequences = [seq, seq.split('').reverse().join('')]; 143 $.each(sequences, function (idx, sequence) { 144 for (j = 0; j < (word.length - 2); j += 1) { // iterate the word trough a sliding window of size 3: 145 if (sequence.indexOf(word.toLowerCase().substring(j, j + 3)) > -1) { 146 found = true; 147 } 148 } 149 }); 150 }); 151 if (found) { return score; } 152 } 153 return 0; 154 }; 155 156 validation.wordLowercase = function (options, word, score) { 157 return word.match(/[a-z]/) && score; 158 }; 159 160 validation.wordUppercase = function (options, word, score) { 161 return word.match(/[A-Z]/) && score; 162 }; 163 164 validation.wordOneNumber = function (options, word, score) { 165 return word.match(/\d+/) && score; 166 }; 167 168 validation.wordThreeNumbers = function (options, word, score) { 169 return word.match(/(.*[0-9].*[0-9].*[0-9])/) && score; 170 }; 171 172 validation.wordOneSpecialChar = function (options, word, score) { 173 return word.match(/[!,@,#,$,%,\^,&,*,?,_,~]/) && score; 174 }; 175 176 validation.wordTwoSpecialChar = function (options, word, score) { 177 return word.match(/(.*[!,@,#,$,%,\^,&,*,?,_,~].*[!,@,#,$,%,\^,&,*,?,_,~])/) && score; 178 }; 179 180 validation.wordUpperLowerCombo = function (options, word, score) { 181 return word.match(/([a-z].*[A-Z])|([A-Z].*[a-z])/) && score; 182 }; 183 184 validation.wordLetterNumberCombo = function (options, word, score) { 185 return word.match(/([a-zA-Z])/) && word.match(/([0-9])/) && score; 186 }; 187 188 validation.wordLetterNumberCharCombo = function (options, word, score) { 189 return word.match(/([a-zA-Z0-9].*[!,@,#,$,%,\^,&,*,?,_,~])|([!,@,#,$,%,\^,&,*,?,_,~].*[a-zA-Z0-9])/) && score; 190 }; 191 192 rulesEngine.validation = validation; 193 194 rulesEngine.executeRules = function (options, word) { 195 var totalScore = 0; 196 197 $.each(options.rules.activated, function (rule, active) { 198 if (active) { 199 var score = options.rules.scores[rule], 200 funct = rulesEngine.validation[rule], 201 result, 202 errorMessage; 203 204 if (!$.isFunction(funct)) { 205 funct = options.rules.extra[rule]; 206 } 207 208 if ($.isFunction(funct)) { 209 result = funct(options, word, score); 210 if (result) {
211 totalScore += result; 212 } 213 if (result < 0 || (!$.isNumeric(result) && !result)) { 214 errorMessage = options.ui.spanError(options, rule); 215 if (errorMessage.length > 0) { 216 options.instances.errors.push(errorMessage); 217 } 218 } 219 } 220 } 221 }); 222 223 if ($.isFunction(options.common.onScore)) { 224 totalScore = options.common.onScore(options, word, totalScore); 225 } 226 227 return totalScore; 228 }; 229}(jQuery, rulesEngine)); 230 231try { 232 if (module && module.exports) { 233 module.exports = rulesEngine; 234 } 235} catch (ignore) {} 236 237// Source: src/options.js 238 239 240 241 242var defaultOptions = {}; 243 244defaultOptions.common = {}; 245defaultOptions.common.minChar = 6; 246defaultOptions.common.maxChar = 20; 247defaultOptions.common.usernameField = "#username"; 248defaultOptions.common.userInputs = [ 249 // Selectors for input fields with user input 250]; 251defaultOptions.common.onLoad = undefined; 252defaultOptions.common.onKeyUp = undefined; 253defaultOptions.common.onScore = undefined; 254defaultOptions.common.zxcvbn = false; 255defaultOptions.common.zxcvbnTerms = [ 256 // List of disrecommended words 257]; 258defaultOptions.common.events = ["keyup", "change", "paste"]; 259defaultOptions.common.debug = false; 260 261defaultOptions.rules = {}; 262defaultOptions.rules.extra = {}; 263defaultOptions.rules.scores = { 264 wordNotEmail: -100, 265 wordMinLength: -50, 266 wordMaxLength: -50, 267 wordInvalidChar: -100, 268 wordSimilarToUsername: -100, 269 wordSequences: -20, 270 wordTwoCharacterClasses: 2, 271 wordRepetitions: -25, 272 wordLowercase: 1, 273 wordUppercase: 3, 274 wordOneNumber: 3, 275 wordThreeNumbers: 5, 276 wordOneSpecialChar: 3, 277 wordTwoSpecialChar: 5, 278 wordUpperLowerCombo: 2, 279 wordLetterNumberCombo: 2, 280 wordLetterNumberCharCombo: 2 281}; 282defaultOptions.rules.activated = { 283 wordNotEmail: true, 284 wordMinLength: true, 285 wordMaxLength: false, 286 wordInvalidChar: false, 287 wordSimilarToUsername: true, 288 wordSequences: true, 289 wordTwoCharacterClasses: false, 290 wordRepetitions: false, 291 wordLowercase: true, 292 wordUppercase: true, 293 wordOneNumber: true, 294 wordThreeNumbers: true, 295 wordOneSpecialChar: true, 296 wordTwoSpecialChar: true, 297 wordUpperLowerCombo: true, 298 wordLetterNumberCombo: true, 299 wordLetterNumberCharCombo: true 300}; 301defaultOptions.rules.raisePower = 1.4; 302 303defaultOptions.ui = {}; 304defaultOptions.ui.bootstrap2 = false; 305defaultOptions.ui.bootstrap4 = false; 306defaultOptions.ui.colorClasses = [ 307 "danger", "danger", "danger", "warning", "warning", "success" 308]; 309defaultOptions.ui.showProgressBar = true; 310defaultOptions.ui.progressBarEmptyPercentage = 1; 311defaultOptions.ui.progressBarMinPercentage = 1; 312defaultOptions.ui.progressExtraCssClasses = ''; 313defaultOptions.ui.progressBarExtraCssClasses = ''; 314defaultOptions.ui.showPopover = false; 315defaultOptions.ui.popoverPlacement = "bottom"; 316defaultOptions.ui.showStatus = false; 317defaultOptions.ui.spanError = function (options, key) { 318 "use strict"; 319 var text = options.i18n.t(key); 320 if (!text) { return ''; } 321 return '<span style="color: #d52929">' + text + '</span>'; 322}; 323defaultOptions.ui.popoverError = function (options) { 324 "use strict"; 325 var errors = options.instances.errors, 326 errorsTitle = options.i18n.t("errorList"), 327 message = "<div>" + errorsTitle + "<ul class='error-list' style='margin-bottom: 0;'>"; 328 329 jQuery.each(errors, function (idx, err) { 330 message += "<li>" + err + "</li>"; 331 }); 332 message += "</ul></div>"; 333 return message; 334}; 335defaultOptions.ui.showVerdicts = true; 336defaultOptions.ui.showVerdictsInsideProgressBar = false; 337defaultOptions.ui.useVerdictCssClass = false; 338defaultOptions.ui.showErrors = false; 339defaultOptions.ui.showScore = false; 340defaultOptions.ui.container = undefined; 341defaultOptions.ui.viewports = { 342 progress: undefined, 343 verdict: undefined, 344 errors: undefined, 345 score: undefined 346}; 347defaultOptions.ui.scores = [0, 14, 26, 38, 50]; 348 349defaultOptions.i18n = {}; 350defaultOptions.i18n.t = i18n.t; 351 352// Source: src/ui.js 353 354 355 356 357var ui = {}; 358 359(function ($, ui) { 360 "use strict"; 361 362 var statusClasses = ["error", "warning", "success"], 363 verdictKeys = [ 364 "veryWeak", "weak", "normal", "medium", "strong", "veryStrong" 365 ]; 366 367 ui.getContainer = function (options, $el) { 368 var $container; 369 370 $container = $(options.ui.container); 371 if (!($container && $container.length === 1)) { 372 $container = $el.parent(); 373 } 374 return $container; 375 }; 376 377 ui.findElement = function ($container, viewport, cssSelector) { 378 if (viewport) { 379 return $container.find(viewport).find(cssSelector); 380 } 381 return $container.find(cssSelector); 382 }; 383 384 ui.getUIElements = function (options, $el) { 385 var $container, result; 386 387 if (options.instances.viewports) { 388 return options.instances.viewports; 389 } 390 391 $container = ui.getContainer(options, $el); 392 393 result = {}; 394 result.$progressbar = ui.findElement($container, options.ui.viewports.progress, "div.progress"); 395 if (options.ui.showVerdictsInsideProgressBar) { 396 result.$verdict = result.$progressbar.find("span.password-verdict"); 397 } 398 399 if (!options.ui.showPopover) { 400 if (!options.ui.showVerdictsInsideProgressBar) { 401 result.$verdict = ui.findElement($container, options.ui.viewports.verdict, "span.password-verdict"); 402 } 403 result.$errors = ui.findElement($container, options.ui.viewports.errors, "ul.error-list"); 404 } 405 result.$score = ui.findElement($container, options.ui.viewports.score, 406 "span.password-score"); 407 408 options.instances.viewports = result; 409 return result; 410 }; 411 412 ui.initProgressBar = function (options, $el) { 413 var $container = ui.getContainer(options, $el), 414 progressbar = "<div class='progress "; 415 416 if (options.ui.bootstrap2) { 417 // Boostrap 2
418 progressbar += options.ui.progressBarExtraCssClasses + 419 "'><div class='"; 420 } else { 421 // Bootstrap 3 & 4 422 progressbar += options.ui.progressExtraCssClasses + "'><div class='" + 423 options.ui.progressBarExtraCssClasses + " progress-"; 424 } 425 progressbar += "bar'>"; 426 427 if (options.ui.showVerdictsInsideProgressBar) { 428 progressbar += "<span class='password-verdict'></span>"; 429 } 430 431 progressbar += "</div></div>"; 432 433 if (options.ui.viewports.progress) { 434 $container.find(options.ui.viewports.progress).append(progressbar); 435 } else { 436 $(progressbar).insertAfter($el); 437 } 438 }; 439 440 ui.initHelper = function (options, $el, html, viewport) { 441 var $container = ui.getContainer(options, $el); 442 if (viewport) { 443 $container.find(viewport).append(html); 444 } else { 445 $(html).insertAfter($el); 446 } 447 }; 448 449 ui.initVerdict = function (options, $el) { 450 ui.initHelper(options, $el, "<span class='password-verdict'></span>", 451 options.ui.viewports.verdict); 452 }; 453 454 ui.initErrorList = function (options, $el) { 455 ui.initHelper(options, $el, "<ul class='error-list'></ul>", 456 options.ui.viewports.errors); 457 }; 458 459 ui.initScore = function (options, $el) { 460 ui.initHelper(options, $el, "<span class='password-score'></span>", 461 options.ui.viewports.score); 462 }; 463 464 ui.initPopover = function (options, $el) { 465 $el.popover("destroy"); 466 $el.popover({ 467 html: true, 468 placement: options.ui.popoverPlacement, 469 trigger: "manual", 470 content: " " 471 }); 472 }; 473 474 ui.initUI = function (options, $el) { 475 if (options.ui.showPopover) { 476 ui.initPopover(options, $el); 477 } else { 478 if (options.ui.showErrors) { ui.initErrorList(options, $el); } 479 if (options.ui.showVerdicts && !options.ui.showVerdictsInsideProgressBar) { 480 ui.initVerdict(options, $el); 481 } 482 } 483 if (options.ui.showProgressBar) { 484 ui.initProgressBar(options, $el); 485 } 486 if (options.ui.showScore) { 487 ui.initScore(options, $el); 488 } 489 }; 490 491 ui.updateProgressBar = function (options, $el, cssClass, percentage) { 492 var $progressbar = ui.getUIElements(options, $el).$progressbar, 493 $bar = $progressbar.find(".progress-bar"), 494 cssPrefix = "progress-"; 495 496 if (options.ui.bootstrap2) { 497 $bar = $progressbar.find(".bar"); 498 cssPrefix = ""; 499 } 500 501 $.each(options.ui.colorClasses, function (idx, value) { 502 if (options.ui.bootstrap4) { 503 $bar.removeClass("bg-" + value); 504 } else { 505 $bar.removeClass(cssPrefix + "bar-" + value); 506 } 507 }); 508 if (options.ui.bootstrap4) { 509 $bar.addClass("bg-" + options.ui.colorClasses[cssClass]); 510 } else { 511 $bar.addClass(cssPrefix + "bar-" + options.ui.colorClasses[cssClass]); 512 } 513 $bar.css("width", percentage + '%'); 514 }; 515 516 ui.updateVerdict = function (options, $el, cssClass, text) { 517 var $verdict = ui.getUIElements(options, $el).$verdict; 518 $verdict.removeClass(options.ui.colorClasses.join(' ')); 519 if (cssClass > -1) { 520 $verdict.addClass(options.ui.colorClasses[cssClass]); 521 } 522 $verdict.html(text); 523 }; 524 525 ui.updateErrors = function (options, $el, remove) { 526 var $errors = ui.getUIElements(options, $el).$errors, 527 html = ""; 528 529 if (!remove) { 530 $.each(options.instances.errors, function (idx, err) { 531 html += "<li>" + err + "</li>"; 532 }); 533 } 534 $errors.html(html); 535 }; 536 537 ui.updateScore = function (options, $el, score, remove) { 538 var $score = ui.getUIElements(options, $el).$score, 539 html = ""; 540 541 if (!remove) { html = score.toFixed(2); } 542 $score.html(html); 543 }; 544 545 ui.updatePopover = function (options, $el, verdictText, remove) { 546 var popover = $el.data("bs.popover"), 547 html = "", 548 hide = true; 549 550 if (options.ui.showVerdicts && 551 !options.ui.showVerdictsInsideProgressBar && 552 verdictText.length > 0) { 553 html = "<h5><span class='password-verdict'>" + verdictText + 554 "</span></h5>"; 555 hide = false;
556 } 557 if (options.ui.showErrors) { 558 if (options.instances.errors.length > 0) { 559 hide = false; 560 } 561 html += options.ui.popoverError(options); 562 } 563 564 if (hide || remove) { 565 $el.popover("hide"); 566 return; 567 } 568 569 if (options.ui.bootstrap2) { popover = $el.data("popover"); } 570 571 if (popover.$arrow && popover.$arrow.parents("body").length > 0) { 572 $el.find("+ .popover .popover-content").html(html); 573 } else { 574 // It's hidden 575 popover.options.content = html; 576 $el.popover("show"); 577 } 578 }; 579 580 ui.updateFieldStatus = function (options, $el, cssClass, remove) { 581 var targetClass = options.ui.bootstrap2 ? ".control-group" : ".form-group", 582 $container = $el.parents(targetClass).first(); 583 584 $.each(statusClasses, function (idx, css) { 585 if (!options.ui.bootstrap2) { css = "has-" + css; } 586 $container.removeClass(css); 587 }); 588 589 if (remove) { return; } 590 591 cssClass = statusClasses[Math.floor(cssClass / 2)]; 592 if (!options.ui.bootstrap2) { cssClass = "has-" + cssClass; } 593 $container.addClass(cssClass); 594 }; 595 596 ui.percentage = function (options, score, maximun) { 597 var result = Math.floor(100 * score / maximun), 598 min = options.ui.progressBarMinPercentage; 599 600 result = result <= min ? min : result; 601 result = result > 100 ? 100 : result; 602 return result; 603 }; 604 605 ui.getVerdictAndCssClass = function (options, score) { 606 var level, verdict; 607 608 if (score === undefined) { return ['', 0]; } 609 610 if (score <= options.ui.scores[0]) { 611 level = 0; 612 } else if (score < options.ui.scores[1]) { 613 level = 1; 614 } else if (score < options.ui.scores[2]) { 615 level = 2; 616 } else if (score < options.ui.scores[3]) { 617 level = 3; 618 } else if (score < options.ui.scores[4]) { 619 level = 4; 620 } else { 621 level = 5; 622 } 623 624 verdict = verdictKeys[level]; 625 626 return [options.i18n.t(verdict), level]; 627 }; 628 629 ui.updateUI = function (options, $el, score) { 630 var cssClass, barPercentage, verdictText, verdictCssClass; 631 632 cssClass = ui.getVerdictAndCssClass(options, score); 633 verdictText = score === 0 ? '' : cssClass[0]; 634 cssClass = cssClass[1]; 635 verdictCssClass = options.ui.useVerdictCssClass ? cssClass : -1; 636 637 if (options.ui.showProgressBar) { 638 if (score === undefined) { 639 barPercentage = options.ui.progressBarEmptyPercentage; 640 } else { 641 barPercentage = ui.percentage(options, score, options.ui.scores[4]); 642 } 643 ui.updateProgressBar(options, $el, cssClass, barPercentage); 644 if (options.ui.showVerdictsInsideProgressBar) { 645 ui.updateVerdict(options, $el, verdictCssClass, verdictText); 646 } 647 } 648 649 if (options.ui.showStatus) { 650 ui.updateFieldStatus(options, $el, cssClass, score === undefined); 651 } 652 653 if (options.ui.showPopover) { 654 ui.updatePopover(options, $el, verdictText, score === undefined); 655 } else { 656 if (options.ui.showVerdicts && !options.ui.showVerdictsInsideProgressBar) { 657 ui.updateVerdict(options, $el, verdictCssClass, verdictText); 658 } 659 if (options.ui.showErrors) { 660 ui.updateErrors(options, $el, score === undefined); 661 } 662 } 663 664 if (options.ui.showScore) { 665 ui.updateScore(options, $el, score, score === undefined); 666 } 667 }; 668}(jQuery, ui)); 669 670// Source: src/methods.js 671 672 673 674 675var methods = {}; 676 677(function ($, methods) { 678 "use strict"; 679 var onKeyUp, onPaste, applyToAll; 680 681 onKeyUp = function (event) { 682 var $el = $(event.target), 683 options = $el.data("pwstrength-bootstrap"), 684 word = $el.val(), 685 userInputs, 686 verdictText, 687 verdictLevel, 688 score; 689 690 if (options === undefined) { return; } 691 692 options.instances.errors = []; 693 if (word.length === 0) { 694 score = undefined; 695 } else { 696 if (options.common.zxcvbn) { 697 userInputs = []; 698 $.each(options.common.userInputs.concat([options.common.usernameField]), function (idx, selector) { 699 var value = $(selector).val(); 700 if (value) { userInputs.push(value); } 701 }); 702 userInputs = userInputs.concat(options.common.zxcvbnTerms); 703 score = zxcvbn(word, userInputs).guesses; 704 score = Math.log(score) * Math.LOG2E; 705 } else { 706 score = rulesEngine.executeRules(options, word); 707 } 708 } 709 ui.updateUI(options, $el, score); 710 verdictText = ui.getVerdictAndCssClass(options, score); 711 verdictLevel = verdictText[1]; 712 verdictText = verdictText[0]; 713 714 if (options.common.debug) { 715 console.log(score + ' - ' + verdictText); 716 } 717 718 if ($.isFunction(options.common.onKeyUp)) { 719 options.common.onKeyUp(event, { 720 score: score, 721 verdictText: verdictText, 722 verdictLevel: verdictLevel 723 }); 724 } 725 }; 726 727 onPaste = function (event) { 728 // This handler is necessary because the paste event fires before the 729 // content is actually in the input, so we cannot read its value right 730 // away. Therefore, the timeouts. 731 var $el = $(event.target), 732 word = $el.val(), 733 tries = 0, 734 callback; 735 736 callback = function () { 737 var newWord = $el.val(); 738 739 if (newWord !== word) { 740 onKeyUp(event); 741 } else if (tries < 3) { 742 tries += 1; 743 setTimeout(callback, 100); 744 } 745 }; 746 747 setTimeout(callback, 100); 748 }; 749 750 methods.init = function (settings) { 751 this.each(function (idx, el) { 752 // Make it deep extend (first param) so it extends also the 753 // rules and other inside objects 754 var clonedDefaults = $.extend(true, {}, defaultOptions), 755 localOptions = $.extend(true, clonedDefaults, settings), 756 $el = $(el); 757 758 localOptions.instances = {}; 759 $el.data("pwstrength-bootstrap", localOptions); 760 761 $.each(localOptions.common.events, function (idx, eventName) { 762 var handler = eventName === "paste" ? onPaste : onKeyUp; 763 $el.on(eventName, handler); 764 }); 765 766 ui.initUI(localOptions, $el); 767 $el.trigger("keyup"); 768 769 if ($.isFunction(localOptions.common.onLoad)) { 770 localOptions.common.onLoad(); 771 } 772 }); 773 774 return this; 775 }; 776 777 methods.destroy = function () { 778 this.each(function (idx, el) { 779 var $el = $(el), 780 options = $el.data("pwstrength-bootstrap"), 781 elements = ui.getUIElements(options, $el); 782 elements.$progressbar.remove(); 783 elements.$verdict.remove(); 784 elements.$errors.remove(); 785 $el.removeData("pwstrength-bootstrap"); 786 }); 787 }; 788 789 methods.forceUpdate = function () { 790 this.each(function (idx, el) { 791 var event = { target: el }; 792 onKeyUp(event); 793 }); 794 }; 795 796 methods.addRule = function (name, method, score, active) { 797 this.each(function (idx, el) { 798 var options = $(el).data("pwstrength-bootstrap"); 799 800 options.rules.activated[name] = active; 801 options.rules.scores[name] = score; 802 options.rules.extra[name] = method; 803 }); 804 }; 805 806 applyToAll = function (rule, prop, value) { 807 this.each(function (idx, el) { 808 $(el).data("pwstrength-bootstrap").rules[prop][rule] = value; 809 }); 810 }; 811 812 methods.changeScore = function (rule, score) { 813 applyToAll.call(this, rule, "scores", score); 814 }; 815 816 methods.ruleActive = function (rule, active) { 817 applyToAll.call(this, rule, "activated", active); 818 }; 819 820 methods.ruleIsMet = function (rule) { 821 if ($.isFunction(rulesEngine.validation[rule])) { 822 if (rule === "wordLength") { 823 rule = "wordLengthStaticScore"; 824 } 825 826 var rulesMetCnt = 0; 827 828 this.each(function (idx, el) { 829 var options = $(el).data("pwstrength-bootstrap"); 830 831 rulesMetCnt += rulesEngine.validation[rule](options, $(el).val(), 1); 832 }); 833 834 return (rulesMetCnt === this.length); 835 } 836 837 $.error("Rule " + rule + " does not exist on jQuery.pwstrength-bootstrap.validation"); 838 }; 839 840 $.fn.pwstrength = function (method) { 841 var result; 842 843 if (methods[method]) { 844 result = methods[method].apply(this, Array.prototype.slice.call(arguments, 1)); 845 } else if (typeof method === "object" || !method) { 846 result = methods.init.apply(this, arguments); 847 } else { 848 $.error("Method " + method + " does not exist on jQuery.pwstrength-bootstrap"); 849 } 850 851 return result; 852 }; 853}(jQuery, methods)); 854}(jQuery));
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.