diff --git a/Makefile b/Makefile index d61b4d5..771a3d8 100644 --- a/Makefile +++ b/Makefile @@ -7,7 +7,7 @@ dist/payform.js: src/payform.coffee $(BIN)coffee -c --no-header -o dist/ src/payform.coffee dist/payform.min.js: dist/payform.js - $(BIN)uglify -s dist/payform.js -o dist/payform.min.js + $(BIN)uglifyjs dist/payform.js -o dist/payform.min.js dist/jquery.payform.js: src/jquery.payform.coffee $(BIN)browserify \ @@ -17,7 +17,7 @@ dist/jquery.payform.js: src/jquery.payform.coffee src/jquery.payform.coffee > dist/jquery.payform.js dist/jquery.payform.min.js: dist/jquery.payform.js - $(BIN)uglify -s dist/jquery.payform.js -o dist/jquery.payform.min.js + $(BIN)uglifyjs dist/jquery.payform.js -o dist/jquery.payform.min.js watch: build $(BIN)watch 'make build' src diff --git a/dist/jquery.payform.js b/dist/jquery.payform.js index 8390b02..10e1211 100644 --- a/dist/jquery.payform.js +++ b/dist/jquery.payform.js @@ -246,6 +246,9 @@ var indexOf = [].indexOf || function(item) { for (var i = 0, l = this.length; i }; reFormatCardNumber = function(e) { var cursor; + if (e.target.value === "") { + return; + } cursor = _getCaretPos(e.target); e.target.value = payform.formatCardNumber(e.target.value); if ((cursor != null) && e.type !== 'change') { @@ -313,6 +316,9 @@ var indexOf = [].indexOf || function(item) { for (var i = 0, l = this.length; i }; reFormatExpiry = function(e) { var cursor; + if (e.target.value === "") { + return; + } cursor = _getCaretPos(e.target); e.target.value = payform.formatCardExpiry(e.target.value); if ((cursor != null) && e.type !== 'change') { @@ -379,6 +385,9 @@ var indexOf = [].indexOf || function(item) { for (var i = 0, l = this.length; i }; reFormatCVC = function(e) { var cursor; + if (e.target.value === "") { + return; + } cursor = _getCaretPos(e.target); e.target.value = replaceFullWidthChars(e.target.value).replace(/\D/g, '').slice(0, 4); if ((cursor != null) && e.type !== 'change') { diff --git a/dist/jquery.payform.min.js b/dist/jquery.payform.min.js index c1cfe61..122c2be 100644 --- a/dist/jquery.payform.min.js +++ b/dist/jquery.payform.min.js @@ -1 +1 @@ -!function a(b,c,d){function e(g,h){if(!c[g]){if(!b[g]){var i="function"==typeof require&&require;if(!h&&i)return i(g,!0);if(f)return f(g,!0);var j=new Error("Cannot find module '"+g+"'");throw j.code="MODULE_NOT_FOUND",j}var k=c[g]={exports:{}};b[g][0].call(k.exports,function(a){var c=b[g][1][a];return e(c?c:a)},k,k.exports,a,b,c,d)}return c[g].exports}for(var f="function"==typeof require&&require,g=0;gb;b++)if(b in this&&this[b]===a)return b;return-1};!function(a,c){return"undefined"!=typeof b&&null!==b?b.exports=c():"function"==typeof define&&"object"==typeof define.amd?define(a,c):this[a]=c()}("payform",function(){var a,b,c,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v,w,x;return b=function(a){var b,c,d;return null!=a.selectionStart?a.selectionStart:null!=document.selection?(a.focus(),b=document.selection.createRange(),d=a.createTextRange(),c=d.duplicate(),d.moveToBookmark(b.getBookmark()),c.setEndPoint("EndToStart",d),c.text.length):void 0},a=function(a){return function(b){return null==b&&(b=window.event),b.target=b.target||b.srcElement,b.which=b.which||b.keyCode,null==b.preventDefault&&(b.preventDefault=function(){return this.returnValue=!1}),a(b)}},c=function(b,c,d){return d=a(d),null!=b.addEventListener?b.addEventListener(c,d,!1):b.attachEvent("on"+c,d)},p={},g=/(\d{1,4})/g,p.cards=[{type:"elo",pattern:/^((50670[7-8])|(506715)|(50671[7-9])|(50672[0-1])|(50672[4-9])|(50673[0-3])|(506739)|(50674[0-8])|(50675[0-3])|(50677[4-8])|(50900[0-9])|(50901[3-9])|(50902[0-9])|(50903[1-9])|(50904[0-9])|(50905[0-9])|(50906[0-4])|(50906[6-9])|(50907[0-2])|(50907[4-5])|(636368)|(636297)|(504175)|(438935)|(40117[8-9])|(45763[1-2])|(457393)|(431274)|(50907[6-9])|(50908[0-9])|(627780))/,format:g,length:[16],cvcLength:[3],luhn:!0},{type:"visaelectron",pattern:/^4(026|17500|405|508|844|91[37])/,format:g,length:[16],cvcLength:[3],luhn:!0},{type:"maestro",pattern:/^(5(018|0[23]|[68])|6(39|7))/,format:g,length:[12,13,14,15,16,17,18,19],cvcLength:[3],luhn:!0},{type:"forbrugsforeningen",pattern:/^600/,format:g,length:[16],cvcLength:[3],luhn:!0},{type:"dankort",pattern:/^5019/,format:g,length:[16],cvcLength:[3],luhn:!0},{type:"visa",pattern:/^4/,format:g,length:[13,16],cvcLength:[3],luhn:!0},{type:"mastercard",pattern:/^(5[1-5]|2[2-7])/,format:g,length:[16],cvcLength:[3],luhn:!0},{type:"amex",pattern:/^3[47]/,format:/(\d{1,4})(\d{1,6})?(\d{1,5})?/,length:[15],cvcLength:[3,4],luhn:!0},{type:"dinersclub",pattern:/^3[0689]/,format:/(\d{1,4})(\d{1,4})?(\d{1,4})?(\d{1,2})?/,length:[14],cvcLength:[3],luhn:!0},{type:"discover",pattern:/^6([045]|22)/,format:g,length:[16],cvcLength:[3],luhn:!0},{type:"unionpay",pattern:/^(62|88)/,format:g,length:[16,17,18,19],cvcLength:[3],luhn:!1},{type:"jcb",pattern:/^35/,format:g,length:[16],cvcLength:[3],luhn:!0}],e=function(a){var b,c,d,e;for(a=(a+"").replace(/\D/g,""),e=p.cards,c=0,d=e.length;d>c;c++)if(b=e[c],b.pattern.test(a))return b},f=function(a){var b,c,d,e;for(e=p.cards,c=0,d=e.length;d>c;c++)if(b=e[c],b.type===a)return b},o=function(a){var b,c,d,e,f,g;for(f=!0,g=0,c=(a+"").split("").reverse(),d=0,e=c.length;e>d;d++)b=c[d],b=parseInt(b,10),(f=!f)&&(b*=2),b>9&&(b-=9),g+=b;return g%10===0},n=function(a){var b;return null!=("undefined"!=typeof document&&null!==document&&null!=(b=document.selection)?b.createRange:void 0)&&document.selection.createRange().text?!0:null!=a.selectionStart&&a.selectionStart!==a.selectionEnd},t=function(a){var b,c,d,e,f,g,h,i;for(null==a&&(a=""),d="0123456789",e="0123456789",i="",c=a.split(""),f=0,h=c.length;h>f;f++)b=c[f],g=d.indexOf(b),g>-1&&(b=e[g]),i+=b;return i},r=function(a){var c;return c=b(a.target),a.target.value=p.formatCardNumber(a.target.value),null!=c&&"change"!==a.type?a.target.setSelectionRange(c,c):void 0},k=function(a){var c,d,f,g,h,i,j;return f=String.fromCharCode(a.which),!/^\d+$/.test(f)||(j=a.target.value,c=e(j+f),g=(j.replace(/\D/g,"")+f).length,i=16,c&&(i=c.length[c.length.length-1]),g>=i||(d=b(a.target),d&&d!==j.length))?void 0:(h=c&&"amex"===c.type?/^(\d{4}|\d{4}\s\d{6})$/:/(?:^|\s)(\d{4})$/,h.test(j)?(a.preventDefault(),setTimeout(function(){return a.target.value=j+" "+f})):h.test(j+f)?(a.preventDefault(),setTimeout(function(){return a.target.value=j+f+" "})):void 0)},h=function(a){var c,d;return d=a.target.value,8!==a.which||(c=b(a.target),c&&c!==d.length)?void 0:/\d\s$/.test(d)?(a.preventDefault(),setTimeout(function(){return a.target.value=d.replace(/\d\s$/,"")})):/\s\d?$/.test(d)?(a.preventDefault(),setTimeout(function(){return a.target.value=d.replace(/\d$/,"")})):void 0},s=function(a){var c;return c=b(a.target),a.target.value=p.formatCardExpiry(a.target.value),null!=c&&"change"!==a.type?a.target.setSelectionRange(c,c):void 0},j=function(a){var b,c;return b=String.fromCharCode(a.which),/^\d+$/.test(b)?(c=a.target.value+b,/^\d$/.test(c)&&"0"!==c&&"1"!==c?(a.preventDefault(),setTimeout(function(){return a.target.value="0"+c+" / "})):/^\d\d$/.test(c)?(a.preventDefault(),setTimeout(function(){return a.target.value=c+" / "})):void 0):void 0},l=function(a){var b,c;return b=String.fromCharCode(a.which),/^\d+$/.test(b)?(c=a.target.value,/^\d\d$/.test(c)?a.target.value=c+" / ":void 0):void 0},m=function(a){var b,c;return c=String.fromCharCode(a.which),"/"===c||" "===c?(b=a.target.value,/^\d$/.test(b)&&"0"!==b?a.target.value="0"+b+" / ":void 0):void 0},i=function(a){var c,d;return d=a.target.value,8!==a.which||(c=b(a.target),c&&c!==d.length)?void 0:/\d\s\/\s$/.test(d)?(a.preventDefault(),setTimeout(function(){return a.target.value=d.replace(/\d\s\/\s$/,"")})):void 0},q=function(a){var c;return c=b(a.target),a.target.value=t(a.target.value).replace(/\D/g,"").slice(0,4),null!=c&&"change"!==a.type?a.target.setSelectionRange(c,c):void 0},x=function(a){var b;if(!(a.metaKey||a.ctrlKey||0===a.which||a.which<33))return b=String.fromCharCode(a.which),/^\d+$/.test(b)?void 0:a.preventDefault()},v=function(a){var b,c,d;return c=String.fromCharCode(a.which),/^\d+$/.test(c)&&!n(a.target)?(d=(a.target.value+c).replace(/\D/g,""),b=e(d),b&&d.length>b.length[b.length.length-1]?a.preventDefault():d.length>16?a.preventDefault():void 0):void 0},w=function(a){var b,c;return b=String.fromCharCode(a.which),/^\d+$/.test(b)&&!n(a.target)?(c=a.target.value+b,c=c.replace(/\D/g,""),c.length>6?a.preventDefault():void 0):void 0},u=function(a){var b,c;return b=String.fromCharCode(a.which),/^\d+$/.test(b)&&!n(a.target)?(c=a.target.value+b,c.length>4?a.preventDefault():void 0):void 0},p.cvcInput=function(a){return c(a,"keypress",x),c(a,"keypress",u),c(a,"paste",q),c(a,"change",q),c(a,"input",q)},p.expiryInput=function(a){return c(a,"keypress",x),c(a,"keypress",w),c(a,"keypress",j),c(a,"keypress",m),c(a,"keypress",l),c(a,"keydown",i),c(a,"change",s),c(a,"input",s)},p.cardNumberInput=function(a){return c(a,"keypress",x),c(a,"keypress",v),c(a,"keypress",k),c(a,"keydown",h),c(a,"paste",r),c(a,"change",r),c(a,"input",r)},p.numericInput=function(a){return c(a,"keypress",x),c(a,"paste",x),c(a,"change",x),c(a,"input",x)},p.parseCardExpiry=function(a){var b,c,d,e;return a=a.replace(/\s/g,""),d=a.split("/",2),b=d[0],e=d[1],2===(null!=e?e.length:void 0)&&/^\d+$/.test(e)&&(c=(new Date).getFullYear(),c=c.toString().slice(0,2),e=c+e),b=parseInt(b,10),e=parseInt(e,10),{month:b,year:e}},p.validateCardNumber=function(a){var b,c;return a=(a+"").replace(/\s+|-/g,""),/^\d+$/.test(a)?(b=e(a),b?(c=a.length,d.call(b.length,c)>=0&&(b.luhn===!1||o(a))):!1):!1},p.validateCardExpiry=function(a,b){var c,d,e;return"object"==typeof a&&"month"in a&&(e=a,a=e.month,b=e.year),a&&b?(a=String(a).trim(),b=String(b).trim(),/^\d+$/.test(a)&&/^\d+$/.test(b)&&a>=1&&12>=a?(2===b.length&&(b=70>b?"20"+b:"19"+b),4!==b.length?!1:(d=new Date(b,a),c=new Date,d.setMonth(d.getMonth()-1),d.setMonth(d.getMonth()+1,1),d>c)):!1):!1},p.validateCardCVC=function(a,b){var c,e;return a=String(a).trim(),/^\d+$/.test(a)?(c=f(b),null!=c?(e=a.length,d.call(c.cvcLength,e)>=0):a.length>=3&&a.length<=4):!1},p.parseCardType=function(a){var b;return a?(null!=(b=e(a))?b.type:void 0)||null:null},p.formatCardNumber=function(a){var b,c,d,f;return a=t(a),a=a.replace(/\D/g,""),(b=e(a))?(f=b.length[b.length.length-1],a=a.slice(0,f),b.format.global?null!=(d=a.match(b.format))?d.join(" "):void 0:(c=b.format.exec(a),null!=c?(c.shift(),c=c.filter(Boolean),c.join(" ")):void 0)):a},p.formatCardExpiry=function(a){var b,c,d,e;return a=t(a),(c=a.match(/^\D*(\d{1,2})(\D+)?(\d{1,4})?/))?(b=c[1]||"",d=c[2]||"",e=c[3]||"",e.length>0?d=" / ":" /"===d?(b=b.substring(0,1),d=""):2===b.length||d.length>0?d=" / ":1===b.length&&"0"!==b&&"1"!==b&&(b="0"+b,d=" / "),b+d+e):""},p})},{}]},{},[1]); \ No newline at end of file +(function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error("Cannot find module '"+o+"'");throw f.code="MODULE_NOT_FOUND",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o9){digit-=9}sum+=digit}return sum%10===0};hasTextSelected=function(target){var ref;if((typeof document!=="undefined"&&document!==null?(ref=document.selection)!=null?ref.createRange:void 0:void 0)!=null){if(document.selection.createRange().text){return true}}return target.selectionStart!=null&&target.selectionStart!==target.selectionEnd};replaceFullWidthChars=function(str){var char,chars,fullWidth,halfWidth,i,idx,len,value;if(str==null){str=""}fullWidth="0123456789";halfWidth="0123456789";value="";chars=str.split("");for(i=0,len=chars.length;i-1){char=halfWidth[idx]}value+=char}return value};reFormatCardNumber=function(e){var cursor;if(e.target.value===""){return}cursor=_getCaretPos(e.target);e.target.value=payform.formatCardNumber(e.target.value);if(cursor!=null&&e.type!=="change"){return e.target.setSelectionRange(cursor,cursor)}};formatCardNumber=function(e){var card,cursor,digit,length,re,upperLength,value;digit=String.fromCharCode(e.which);if(!/^\d+$/.test(digit)){return}value=e.target.value;card=cardFromNumber(value+digit);length=(value.replace(/\D/g,"")+digit).length;upperLength=16;if(card){upperLength=card.length[card.length.length-1]}if(length>=upperLength){return}cursor=_getCaretPos(e.target);if(cursor&&cursor!==value.length){return}if(card&&card.type==="amex"){re=/^(\d{4}|\d{4}\s\d{6})$/}else{re=/(?:^|\s)(\d{4})$/}if(re.test(value)){e.preventDefault();return setTimeout(function(){return e.target.value=value+" "+digit})}else if(re.test(value+digit)){e.preventDefault();return setTimeout(function(){return e.target.value=value+digit+" "})}};formatBackCardNumber=function(e){var cursor,value;value=e.target.value;if(e.which!==8){return}cursor=_getCaretPos(e.target);if(cursor&&cursor!==value.length){return}if(/\d\s$/.test(value)){e.preventDefault();return setTimeout(function(){return e.target.value=value.replace(/\d\s$/,"")})}else if(/\s\d?$/.test(value)){e.preventDefault();return setTimeout(function(){return e.target.value=value.replace(/\d$/,"")})}};reFormatExpiry=function(e){var cursor;if(e.target.value===""){return}cursor=_getCaretPos(e.target);e.target.value=payform.formatCardExpiry(e.target.value);if(cursor!=null&&e.type!=="change"){return e.target.setSelectionRange(cursor,cursor)}};formatCardExpiry=function(e){var digit,val;digit=String.fromCharCode(e.which);if(!/^\d+$/.test(digit)){return}val=e.target.value+digit;if(/^\d$/.test(val)&&(val!=="0"&&val!=="1")){e.preventDefault();return setTimeout(function(){return e.target.value="0"+val+" / "})}else if(/^\d\d$/.test(val)){e.preventDefault();return setTimeout(function(){return e.target.value=val+" / "})}};formatForwardExpiry=function(e){var digit,val;digit=String.fromCharCode(e.which);if(!/^\d+$/.test(digit)){return}val=e.target.value;if(/^\d\d$/.test(val)){return e.target.value=val+" / "}};formatForwardSlashAndSpace=function(e){var val,which;which=String.fromCharCode(e.which);if(!(which==="/"||which===" ")){return}val=e.target.value;if(/^\d$/.test(val)&&val!=="0"){return e.target.value="0"+val+" / "}};formatBackExpiry=function(e){var cursor,value;value=e.target.value;if(e.which!==8){return}cursor=_getCaretPos(e.target);if(cursor&&cursor!==value.length){return}if(/\d\s\/\s$/.test(value)){e.preventDefault();return setTimeout(function(){return e.target.value=value.replace(/\d\s\/\s$/,"")})}};reFormatCVC=function(e){var cursor;if(e.target.value===""){return}cursor=_getCaretPos(e.target);e.target.value=replaceFullWidthChars(e.target.value).replace(/\D/g,"").slice(0,4);if(cursor!=null&&e.type!=="change"){return e.target.setSelectionRange(cursor,cursor)}};restrictNumeric=function(e){var input;if(e.metaKey||e.ctrlKey){return}if(e.which===0){return}if(e.which<33){return}input=String.fromCharCode(e.which);if(!/^\d+$/.test(input)){return e.preventDefault()}};restrictCardNumber=function(e){var card,digit,value;digit=String.fromCharCode(e.which);if(!/^\d+$/.test(digit)){return}if(hasTextSelected(e.target)){return}value=(e.target.value+digit).replace(/\D/g,"");card=cardFromNumber(value);if(card&&value.length>card.length[card.length.length-1]){return e.preventDefault()}else if(value.length>16){return e.preventDefault()}};restrictExpiry=function(e){var digit,value;digit=String.fromCharCode(e.which);if(!/^\d+$/.test(digit)){return}if(hasTextSelected(e.target)){return}value=e.target.value+digit;value=value.replace(/\D/g,"");if(value.length>6){return e.preventDefault()}};restrictCVC=function(e){var digit,val;digit=String.fromCharCode(e.which);if(!/^\d+$/.test(digit)){return}if(hasTextSelected(e.target)){return}val=e.target.value+digit;if(val.length>4){return e.preventDefault()}};payform.cvcInput=function(input){_on(input,"keypress",restrictNumeric);_on(input,"keypress",restrictCVC);_on(input,"paste",reFormatCVC);_on(input,"change",reFormatCVC);return _on(input,"input",reFormatCVC)};payform.expiryInput=function(input){_on(input,"keypress",restrictNumeric);_on(input,"keypress",restrictExpiry);_on(input,"keypress",formatCardExpiry);_on(input,"keypress",formatForwardSlashAndSpace);_on(input,"keypress",formatForwardExpiry);_on(input,"keydown",formatBackExpiry);_on(input,"change",reFormatExpiry);return _on(input,"input",reFormatExpiry)};payform.cardNumberInput=function(input){_on(input,"keypress",restrictNumeric);_on(input,"keypress",restrictCardNumber);_on(input,"keypress",formatCardNumber);_on(input,"keydown",formatBackCardNumber);_on(input,"paste",reFormatCardNumber);_on(input,"change",reFormatCardNumber);return _on(input,"input",reFormatCardNumber)};payform.numericInput=function(input){_on(input,"keypress",restrictNumeric);_on(input,"paste",restrictNumeric);_on(input,"change",restrictNumeric);return _on(input,"input",restrictNumeric)};payform.parseCardExpiry=function(value){var month,prefix,ref,year;value=value.replace(/\s/g,"");ref=value.split("/",2),month=ref[0],year=ref[1];if((year!=null?year.length:void 0)===2&&/^\d+$/.test(year)){prefix=(new Date).getFullYear();prefix=prefix.toString().slice(0,2);year=prefix+year}month=parseInt(month,10);year=parseInt(year,10);return{month:month,year:year}};payform.validateCardNumber=function(num){var card,ref;num=(num+"").replace(/\s+|-/g,"");if(!/^\d+$/.test(num)){return false}card=cardFromNumber(num);if(!card){return false}return(ref=num.length,indexOf.call(card.length,ref)>=0)&&(card.luhn===false||luhnCheck(num))};payform.validateCardExpiry=function(month,year){var currentTime,expiry,ref;if(typeof month==="object"&&"month"in month){ref=month,month=ref.month,year=ref.year}if(!(month&&year)){return false}month=String(month).trim();year=String(year).trim();if(!/^\d+$/.test(month)){return false}if(!/^\d+$/.test(year)){return false}if(!(1<=month&&month<=12)){return false}if(year.length===2){if(year<70){year="20"+year}else{year="19"+year}}if(year.length!==4){return false}expiry=new Date(year,month);currentTime=new Date;expiry.setMonth(expiry.getMonth()-1);expiry.setMonth(expiry.getMonth()+1,1);return expiry>currentTime};payform.validateCardCVC=function(cvc,type){var card,ref;cvc=String(cvc).trim();if(!/^\d+$/.test(cvc)){return false}card=cardFromType(type);if(card!=null){return ref=cvc.length,indexOf.call(card.cvcLength,ref)>=0}else{return cvc.length>=3&&cvc.length<=4}};payform.parseCardType=function(num){var ref;if(!num){return null}return((ref=cardFromNumber(num))!=null?ref.type:void 0)||null};payform.formatCardNumber=function(num){var card,groups,ref,upperLength;num=replaceFullWidthChars(num);num=num.replace(/\D/g,"");card=cardFromNumber(num);if(!card){return num}upperLength=card.length[card.length.length-1];num=num.slice(0,upperLength);if(card.format.global){return(ref=num.match(card.format))!=null?ref.join(" "):void 0}else{groups=card.format.exec(num);if(groups==null){return}groups.shift();groups=groups.filter(Boolean);return groups.join(" ")}};payform.formatCardExpiry=function(expiry){var mon,parts,sep,year;expiry=replaceFullWidthChars(expiry);parts=expiry.match(/^\D*(\d{1,2})(\D+)?(\d{1,4})?/);if(!parts){return""}mon=parts[1]||"";sep=parts[2]||"";year=parts[3]||"";if(year.length>0){sep=" / "}else if(sep===" /"){mon=mon.substring(0,1);sep=""}else if(mon.length===2||sep.length>0){sep=" / "}else if(mon.length===1&&(mon!=="0"&&mon!=="1")){mon="0"+mon;sep=" / "}return mon+sep+year};return payform})},{}]},{},[1]); \ No newline at end of file diff --git a/dist/payform.js b/dist/payform.js index fa510f1..506a90c 100644 --- a/dist/payform.js +++ b/dist/payform.js @@ -216,6 +216,9 @@ }; reFormatCardNumber = function(e) { var cursor; + if (e.target.value === "") { + return; + } cursor = _getCaretPos(e.target); e.target.value = payform.formatCardNumber(e.target.value); if ((cursor != null) && e.type !== 'change') { @@ -283,6 +286,9 @@ }; reFormatExpiry = function(e) { var cursor; + if (e.target.value === "") { + return; + } cursor = _getCaretPos(e.target); e.target.value = payform.formatCardExpiry(e.target.value); if ((cursor != null) && e.type !== 'change') { @@ -349,6 +355,9 @@ }; reFormatCVC = function(e) { var cursor; + if (e.target.value === "") { + return; + } cursor = _getCaretPos(e.target); e.target.value = replaceFullWidthChars(e.target.value).replace(/\D/g, '').slice(0, 4); if ((cursor != null) && e.type !== 'change') { diff --git a/dist/payform.min.js b/dist/payform.min.js index 7c9feb4..bd9e591 100644 --- a/dist/payform.min.js +++ b/dist/payform.min.js @@ -1 +1 @@ -(function(){var a=[].indexOf||function(a){for(var b=0,c=this.length;c>b;b++)if(b in this&&this[b]===a)return b;return-1};!function(a,b){return"undefined"!=typeof module&&null!==module?module.exports=b():"function"==typeof define&&"object"==typeof define.amd?define(a,b):this[a]=b()}("payform",function(){var b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v,w,x;return c=function(a){var b,c,d;return null!=a.selectionStart?a.selectionStart:null!=document.selection?(a.focus(),b=document.selection.createRange(),d=a.createTextRange(),c=d.duplicate(),d.moveToBookmark(b.getBookmark()),c.setEndPoint("EndToStart",d),c.text.length):void 0},b=function(a){return function(b){return null==b&&(b=window.event),b.target=b.target||b.srcElement,b.which=b.which||b.keyCode,null==b.preventDefault&&(b.preventDefault=function(){return this.returnValue=!1}),a(b)}},d=function(a,c,d){return d=b(d),null!=a.addEventListener?a.addEventListener(c,d,!1):a.attachEvent("on"+c,d)},p={},g=/(\d{1,4})/g,p.cards=[{type:"elo",pattern:/^((50670[7-8])|(506715)|(50671[7-9])|(50672[0-1])|(50672[4-9])|(50673[0-3])|(506739)|(50674[0-8])|(50675[0-3])|(50677[4-8])|(50900[0-9])|(50901[3-9])|(50902[0-9])|(50903[1-9])|(50904[0-9])|(50905[0-9])|(50906[0-4])|(50906[6-9])|(50907[0-2])|(50907[4-5])|(636368)|(636297)|(504175)|(438935)|(40117[8-9])|(45763[1-2])|(457393)|(431274)|(50907[6-9])|(50908[0-9])|(627780))/,format:g,length:[16],cvcLength:[3],luhn:!0},{type:"visaelectron",pattern:/^4(026|17500|405|508|844|91[37])/,format:g,length:[16],cvcLength:[3],luhn:!0},{type:"maestro",pattern:/^(5(018|0[23]|[68])|6(39|7))/,format:g,length:[12,13,14,15,16,17,18,19],cvcLength:[3],luhn:!0},{type:"forbrugsforeningen",pattern:/^600/,format:g,length:[16],cvcLength:[3],luhn:!0},{type:"dankort",pattern:/^5019/,format:g,length:[16],cvcLength:[3],luhn:!0},{type:"visa",pattern:/^4/,format:g,length:[13,16],cvcLength:[3],luhn:!0},{type:"mastercard",pattern:/^(5[1-5]|2[2-7])/,format:g,length:[16],cvcLength:[3],luhn:!0},{type:"amex",pattern:/^3[47]/,format:/(\d{1,4})(\d{1,6})?(\d{1,5})?/,length:[15],cvcLength:[3,4],luhn:!0},{type:"dinersclub",pattern:/^3[0689]/,format:/(\d{1,4})(\d{1,4})?(\d{1,4})?(\d{1,2})?/,length:[14],cvcLength:[3],luhn:!0},{type:"discover",pattern:/^6([045]|22)/,format:g,length:[16],cvcLength:[3],luhn:!0},{type:"unionpay",pattern:/^(62|88)/,format:g,length:[16,17,18,19],cvcLength:[3],luhn:!1},{type:"jcb",pattern:/^35/,format:g,length:[16],cvcLength:[3],luhn:!0}],e=function(a){var b,c,d,e;for(a=(a+"").replace(/\D/g,""),e=p.cards,c=0,d=e.length;d>c;c++)if(b=e[c],b.pattern.test(a))return b},f=function(a){var b,c,d,e;for(e=p.cards,c=0,d=e.length;d>c;c++)if(b=e[c],b.type===a)return b},o=function(a){var b,c,d,e,f,g;for(f=!0,g=0,c=(a+"").split("").reverse(),d=0,e=c.length;e>d;d++)b=c[d],b=parseInt(b,10),(f=!f)&&(b*=2),b>9&&(b-=9),g+=b;return g%10===0},n=function(a){var b;return null!=("undefined"!=typeof document&&null!==document&&null!=(b=document.selection)?b.createRange:void 0)&&document.selection.createRange().text?!0:null!=a.selectionStart&&a.selectionStart!==a.selectionEnd},t=function(a){var b,c,d,e,f,g,h,i;for(null==a&&(a=""),d="0123456789",e="0123456789",i="",c=a.split(""),f=0,h=c.length;h>f;f++)b=c[f],g=d.indexOf(b),g>-1&&(b=e[g]),i+=b;return i},r=function(a){var b;return b=c(a.target),a.target.value=p.formatCardNumber(a.target.value),null!=b&&"change"!==a.type?a.target.setSelectionRange(b,b):void 0},k=function(a){var b,d,f,g,h,i,j;return f=String.fromCharCode(a.which),!/^\d+$/.test(f)||(j=a.target.value,b=e(j+f),g=(j.replace(/\D/g,"")+f).length,i=16,b&&(i=b.length[b.length.length-1]),g>=i||(d=c(a.target),d&&d!==j.length))?void 0:(h=b&&"amex"===b.type?/^(\d{4}|\d{4}\s\d{6})$/:/(?:^|\s)(\d{4})$/,h.test(j)?(a.preventDefault(),setTimeout(function(){return a.target.value=j+" "+f})):h.test(j+f)?(a.preventDefault(),setTimeout(function(){return a.target.value=j+f+" "})):void 0)},h=function(a){var b,d;return d=a.target.value,8!==a.which||(b=c(a.target),b&&b!==d.length)?void 0:/\d\s$/.test(d)?(a.preventDefault(),setTimeout(function(){return a.target.value=d.replace(/\d\s$/,"")})):/\s\d?$/.test(d)?(a.preventDefault(),setTimeout(function(){return a.target.value=d.replace(/\d$/,"")})):void 0},s=function(a){var b;return b=c(a.target),a.target.value=p.formatCardExpiry(a.target.value),null!=b&&"change"!==a.type?a.target.setSelectionRange(b,b):void 0},j=function(a){var b,c;return b=String.fromCharCode(a.which),/^\d+$/.test(b)?(c=a.target.value+b,/^\d$/.test(c)&&"0"!==c&&"1"!==c?(a.preventDefault(),setTimeout(function(){return a.target.value="0"+c+" / "})):/^\d\d$/.test(c)?(a.preventDefault(),setTimeout(function(){return a.target.value=c+" / "})):void 0):void 0},l=function(a){var b,c;return b=String.fromCharCode(a.which),/^\d+$/.test(b)?(c=a.target.value,/^\d\d$/.test(c)?a.target.value=c+" / ":void 0):void 0},m=function(a){var b,c;return c=String.fromCharCode(a.which),"/"===c||" "===c?(b=a.target.value,/^\d$/.test(b)&&"0"!==b?a.target.value="0"+b+" / ":void 0):void 0},i=function(a){var b,d;return d=a.target.value,8!==a.which||(b=c(a.target),b&&b!==d.length)?void 0:/\d\s\/\s$/.test(d)?(a.preventDefault(),setTimeout(function(){return a.target.value=d.replace(/\d\s\/\s$/,"")})):void 0},q=function(a){var b;return b=c(a.target),a.target.value=t(a.target.value).replace(/\D/g,"").slice(0,4),null!=b&&"change"!==a.type?a.target.setSelectionRange(b,b):void 0},x=function(a){var b;if(!(a.metaKey||a.ctrlKey||0===a.which||a.which<33))return b=String.fromCharCode(a.which),/^\d+$/.test(b)?void 0:a.preventDefault()},v=function(a){var b,c,d;return c=String.fromCharCode(a.which),/^\d+$/.test(c)&&!n(a.target)?(d=(a.target.value+c).replace(/\D/g,""),b=e(d),b&&d.length>b.length[b.length.length-1]?a.preventDefault():d.length>16?a.preventDefault():void 0):void 0},w=function(a){var b,c;return b=String.fromCharCode(a.which),/^\d+$/.test(b)&&!n(a.target)?(c=a.target.value+b,c=c.replace(/\D/g,""),c.length>6?a.preventDefault():void 0):void 0},u=function(a){var b,c;return b=String.fromCharCode(a.which),/^\d+$/.test(b)&&!n(a.target)?(c=a.target.value+b,c.length>4?a.preventDefault():void 0):void 0},p.cvcInput=function(a){return d(a,"keypress",x),d(a,"keypress",u),d(a,"paste",q),d(a,"change",q),d(a,"input",q)},p.expiryInput=function(a){return d(a,"keypress",x),d(a,"keypress",w),d(a,"keypress",j),d(a,"keypress",m),d(a,"keypress",l),d(a,"keydown",i),d(a,"change",s),d(a,"input",s)},p.cardNumberInput=function(a){return d(a,"keypress",x),d(a,"keypress",v),d(a,"keypress",k),d(a,"keydown",h),d(a,"paste",r),d(a,"change",r),d(a,"input",r)},p.numericInput=function(a){return d(a,"keypress",x),d(a,"paste",x),d(a,"change",x),d(a,"input",x)},p.parseCardExpiry=function(a){var b,c,d,e;return a=a.replace(/\s/g,""),d=a.split("/",2),b=d[0],e=d[1],2===(null!=e?e.length:void 0)&&/^\d+$/.test(e)&&(c=(new Date).getFullYear(),c=c.toString().slice(0,2),e=c+e),b=parseInt(b,10),e=parseInt(e,10),{month:b,year:e}},p.validateCardNumber=function(b){var c,d;return b=(b+"").replace(/\s+|-/g,""),/^\d+$/.test(b)?(c=e(b),c?(d=b.length,a.call(c.length,d)>=0&&(c.luhn===!1||o(b))):!1):!1},p.validateCardExpiry=function(a,b){var c,d,e;return"object"==typeof a&&"month"in a&&(e=a,a=e.month,b=e.year),a&&b?(a=String(a).trim(),b=String(b).trim(),/^\d+$/.test(a)&&/^\d+$/.test(b)&&a>=1&&12>=a?(2===b.length&&(b=70>b?"20"+b:"19"+b),4!==b.length?!1:(d=new Date(b,a),c=new Date,d.setMonth(d.getMonth()-1),d.setMonth(d.getMonth()+1,1),d>c)):!1):!1},p.validateCardCVC=function(b,c){var d,e;return b=String(b).trim(),/^\d+$/.test(b)?(d=f(c),null!=d?(e=b.length,a.call(d.cvcLength,e)>=0):b.length>=3&&b.length<=4):!1},p.parseCardType=function(a){var b;return a?(null!=(b=e(a))?b.type:void 0)||null:null},p.formatCardNumber=function(a){var b,c,d,f;return a=t(a),a=a.replace(/\D/g,""),(b=e(a))?(f=b.length[b.length.length-1],a=a.slice(0,f),b.format.global?null!=(d=a.match(b.format))?d.join(" "):void 0:(c=b.format.exec(a),null!=c?(c.shift(),c=c.filter(Boolean),c.join(" ")):void 0)):a},p.formatCardExpiry=function(a){var b,c,d,e;return a=t(a),(c=a.match(/^\D*(\d{1,2})(\D+)?(\d{1,4})?/))?(b=c[1]||"",d=c[2]||"",e=c[3]||"",e.length>0?d=" / ":" /"===d?(b=b.substring(0,1),d=""):2===b.length||d.length>0?d=" / ":1===b.length&&"0"!==b&&"1"!==b&&(b="0"+b,d=" / "),b+d+e):""},p})}).call(this); \ No newline at end of file +(function(){var indexOf=[].indexOf||function(item){for(var i=0,l=this.length;i9){digit-=9}sum+=digit}return sum%10===0};hasTextSelected=function(target){var ref;if((typeof document!=="undefined"&&document!==null?(ref=document.selection)!=null?ref.createRange:void 0:void 0)!=null){if(document.selection.createRange().text){return true}}return target.selectionStart!=null&&target.selectionStart!==target.selectionEnd};replaceFullWidthChars=function(str){var char,chars,fullWidth,halfWidth,i,idx,len,value;if(str==null){str=""}fullWidth="0123456789";halfWidth="0123456789";value="";chars=str.split("");for(i=0,len=chars.length;i-1){char=halfWidth[idx]}value+=char}return value};reFormatCardNumber=function(e){var cursor;if(e.target.value===""){return}cursor=_getCaretPos(e.target);e.target.value=payform.formatCardNumber(e.target.value);if(cursor!=null&&e.type!=="change"){return e.target.setSelectionRange(cursor,cursor)}};formatCardNumber=function(e){var card,cursor,digit,length,re,upperLength,value;digit=String.fromCharCode(e.which);if(!/^\d+$/.test(digit)){return}value=e.target.value;card=cardFromNumber(value+digit);length=(value.replace(/\D/g,"")+digit).length;upperLength=16;if(card){upperLength=card.length[card.length.length-1]}if(length>=upperLength){return}cursor=_getCaretPos(e.target);if(cursor&&cursor!==value.length){return}if(card&&card.type==="amex"){re=/^(\d{4}|\d{4}\s\d{6})$/}else{re=/(?:^|\s)(\d{4})$/}if(re.test(value)){e.preventDefault();return setTimeout(function(){return e.target.value=value+" "+digit})}else if(re.test(value+digit)){e.preventDefault();return setTimeout(function(){return e.target.value=value+digit+" "})}};formatBackCardNumber=function(e){var cursor,value;value=e.target.value;if(e.which!==8){return}cursor=_getCaretPos(e.target);if(cursor&&cursor!==value.length){return}if(/\d\s$/.test(value)){e.preventDefault();return setTimeout(function(){return e.target.value=value.replace(/\d\s$/,"")})}else if(/\s\d?$/.test(value)){e.preventDefault();return setTimeout(function(){return e.target.value=value.replace(/\d$/,"")})}};reFormatExpiry=function(e){var cursor;if(e.target.value===""){return}cursor=_getCaretPos(e.target);e.target.value=payform.formatCardExpiry(e.target.value);if(cursor!=null&&e.type!=="change"){return e.target.setSelectionRange(cursor,cursor)}};formatCardExpiry=function(e){var digit,val;digit=String.fromCharCode(e.which);if(!/^\d+$/.test(digit)){return}val=e.target.value+digit;if(/^\d$/.test(val)&&(val!=="0"&&val!=="1")){e.preventDefault();return setTimeout(function(){return e.target.value="0"+val+" / "})}else if(/^\d\d$/.test(val)){e.preventDefault();return setTimeout(function(){return e.target.value=val+" / "})}};formatForwardExpiry=function(e){var digit,val;digit=String.fromCharCode(e.which);if(!/^\d+$/.test(digit)){return}val=e.target.value;if(/^\d\d$/.test(val)){return e.target.value=val+" / "}};formatForwardSlashAndSpace=function(e){var val,which;which=String.fromCharCode(e.which);if(!(which==="/"||which===" ")){return}val=e.target.value;if(/^\d$/.test(val)&&val!=="0"){return e.target.value="0"+val+" / "}};formatBackExpiry=function(e){var cursor,value;value=e.target.value;if(e.which!==8){return}cursor=_getCaretPos(e.target);if(cursor&&cursor!==value.length){return}if(/\d\s\/\s$/.test(value)){e.preventDefault();return setTimeout(function(){return e.target.value=value.replace(/\d\s\/\s$/,"")})}};reFormatCVC=function(e){var cursor;if(e.target.value===""){return}cursor=_getCaretPos(e.target);e.target.value=replaceFullWidthChars(e.target.value).replace(/\D/g,"").slice(0,4);if(cursor!=null&&e.type!=="change"){return e.target.setSelectionRange(cursor,cursor)}};restrictNumeric=function(e){var input;if(e.metaKey||e.ctrlKey){return}if(e.which===0){return}if(e.which<33){return}input=String.fromCharCode(e.which);if(!/^\d+$/.test(input)){return e.preventDefault()}};restrictCardNumber=function(e){var card,digit,value;digit=String.fromCharCode(e.which);if(!/^\d+$/.test(digit)){return}if(hasTextSelected(e.target)){return}value=(e.target.value+digit).replace(/\D/g,"");card=cardFromNumber(value);if(card&&value.length>card.length[card.length.length-1]){return e.preventDefault()}else if(value.length>16){return e.preventDefault()}};restrictExpiry=function(e){var digit,value;digit=String.fromCharCode(e.which);if(!/^\d+$/.test(digit)){return}if(hasTextSelected(e.target)){return}value=e.target.value+digit;value=value.replace(/\D/g,"");if(value.length>6){return e.preventDefault()}};restrictCVC=function(e){var digit,val;digit=String.fromCharCode(e.which);if(!/^\d+$/.test(digit)){return}if(hasTextSelected(e.target)){return}val=e.target.value+digit;if(val.length>4){return e.preventDefault()}};payform.cvcInput=function(input){_on(input,"keypress",restrictNumeric);_on(input,"keypress",restrictCVC);_on(input,"paste",reFormatCVC);_on(input,"change",reFormatCVC);return _on(input,"input",reFormatCVC)};payform.expiryInput=function(input){_on(input,"keypress",restrictNumeric);_on(input,"keypress",restrictExpiry);_on(input,"keypress",formatCardExpiry);_on(input,"keypress",formatForwardSlashAndSpace);_on(input,"keypress",formatForwardExpiry);_on(input,"keydown",formatBackExpiry);_on(input,"change",reFormatExpiry);return _on(input,"input",reFormatExpiry)};payform.cardNumberInput=function(input){_on(input,"keypress",restrictNumeric);_on(input,"keypress",restrictCardNumber);_on(input,"keypress",formatCardNumber);_on(input,"keydown",formatBackCardNumber);_on(input,"paste",reFormatCardNumber);_on(input,"change",reFormatCardNumber);return _on(input,"input",reFormatCardNumber)};payform.numericInput=function(input){_on(input,"keypress",restrictNumeric);_on(input,"paste",restrictNumeric);_on(input,"change",restrictNumeric);return _on(input,"input",restrictNumeric)};payform.parseCardExpiry=function(value){var month,prefix,ref,year;value=value.replace(/\s/g,"");ref=value.split("/",2),month=ref[0],year=ref[1];if((year!=null?year.length:void 0)===2&&/^\d+$/.test(year)){prefix=(new Date).getFullYear();prefix=prefix.toString().slice(0,2);year=prefix+year}month=parseInt(month,10);year=parseInt(year,10);return{month:month,year:year}};payform.validateCardNumber=function(num){var card,ref;num=(num+"").replace(/\s+|-/g,"");if(!/^\d+$/.test(num)){return false}card=cardFromNumber(num);if(!card){return false}return(ref=num.length,indexOf.call(card.length,ref)>=0)&&(card.luhn===false||luhnCheck(num))};payform.validateCardExpiry=function(month,year){var currentTime,expiry,ref;if(typeof month==="object"&&"month"in month){ref=month,month=ref.month,year=ref.year}if(!(month&&year)){return false}month=String(month).trim();year=String(year).trim();if(!/^\d+$/.test(month)){return false}if(!/^\d+$/.test(year)){return false}if(!(1<=month&&month<=12)){return false}if(year.length===2){if(year<70){year="20"+year}else{year="19"+year}}if(year.length!==4){return false}expiry=new Date(year,month);currentTime=new Date;expiry.setMonth(expiry.getMonth()-1);expiry.setMonth(expiry.getMonth()+1,1);return expiry>currentTime};payform.validateCardCVC=function(cvc,type){var card,ref;cvc=String(cvc).trim();if(!/^\d+$/.test(cvc)){return false}card=cardFromType(type);if(card!=null){return ref=cvc.length,indexOf.call(card.cvcLength,ref)>=0}else{return cvc.length>=3&&cvc.length<=4}};payform.parseCardType=function(num){var ref;if(!num){return null}return((ref=cardFromNumber(num))!=null?ref.type:void 0)||null};payform.formatCardNumber=function(num){var card,groups,ref,upperLength;num=replaceFullWidthChars(num);num=num.replace(/\D/g,"");card=cardFromNumber(num);if(!card){return num}upperLength=card.length[card.length.length-1];num=num.slice(0,upperLength);if(card.format.global){return(ref=num.match(card.format))!=null?ref.join(" "):void 0}else{groups=card.format.exec(num);if(groups==null){return}groups.shift();groups=groups.filter(Boolean);return groups.join(" ")}};payform.formatCardExpiry=function(expiry){var mon,parts,sep,year;expiry=replaceFullWidthChars(expiry);parts=expiry.match(/^\D*(\d{1,2})(\D+)?(\d{1,4})?/);if(!parts){return""}mon=parts[1]||"";sep=parts[2]||"";year=parts[3]||"";if(year.length>0){sep=" / "}else if(sep===" /"){mon=mon.substring(0,1);sep=""}else if(mon.length===2||sep.length>0){sep=" / "}else if(mon.length===1&&(mon!=="0"&&mon!=="1")){mon="0"+mon;sep=" / "}return mon+sep+year};return payform})}).call(this); \ No newline at end of file diff --git a/package.json b/package.json index 0bf9936..e461188 100644 --- a/package.json +++ b/package.json @@ -27,12 +27,12 @@ "watch": "make watch" }, "devDependencies": { - "coffee-script": "~1.9.0", - "watch": "~0.13.0", - "uglify": "~0.1.1", - "mocha": "~2.1.0", "browserify": "~8.1.3", + "bundle-collapser": "~1.1.1", + "coffee-script": "~1.9.0", "coffeeify": "~1.0.0", - "bundle-collapser": "~1.1.1" + "mocha": "~2.1.0", + "uglify-js": "^3.2.2", + "watch": "~0.13.0" } } diff --git a/src/payform.coffee b/src/payform.coffee index a565600..b5e0cb9 100644 --- a/src/payform.coffee +++ b/src/payform.coffee @@ -198,6 +198,7 @@ # Format Card Number reFormatCardNumber = (e) -> + return if e.target.value is "" cursor = _getCaretPos(e.target) e.target.value = payform.formatCardNumber(e.target.value) if cursor? and e.type isnt 'change' @@ -258,6 +259,7 @@ # Format Expiry reFormatExpiry = (e) -> + return if e.target.value is "" cursor = _getCaretPos(e.target) e.target.value = payform.formatCardExpiry(e.target.value) if cursor? and e.type isnt 'change' @@ -310,6 +312,7 @@ # Format CVC reFormatCVC = (e) -> + return if e.target.value is "" cursor = _getCaretPos(e.target) e.target.value = replaceFullWidthChars(e.target.value).replace(/\D/g, '')[0...4] if cursor? and e.type isnt 'change'