autonumeric-rails 1.9.42 → 1.9.43

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 476453bed29c427d18ee7ad9b9b2a7409d6938d9
4
- data.tar.gz: f67a388acd21538c0af5eec413ca5b503e6a8102
3
+ metadata.gz: 9ed549bef320d06305343a6e57f2fc1d49092eea
4
+ data.tar.gz: 785838c92068d1cc922ac4afc68e15509b54843e
5
5
  SHA512:
6
- metadata.gz: d1c9f5409c82a95dc2c848ca36c1653325d4166990ab8408036b2ca7629a4ed151ea1e1e7d49fd03bc196a1bc45e6908188794c7c089690a679ffcbb2d614eec
7
- data.tar.gz: 29f6f16d8da940d454ca70e24dfd87fe893e87828ce7da19136433e5dba1b28b9ba9987b0557071cec0cef812379f40b11d31afcb9bf4cb679f1f6ef3ef48ccf
6
+ metadata.gz: 37e5cc8999fe10f3cbec6a598f516a901215e9139ae0e9c8d5076d4999b8708e971e7045186e818ecc3b43143185488d50620ad24e21131baa3975dda7bacc61
7
+ data.tar.gz: e537770091e2a11bc4ed0bdf94863655f8b2bf12bf2972c9195d07d802dd0cc80acc108ebafb28cd345e844624d025d52a42dd039656ae8615a35dab0e62aacf
data/.gitignore CHANGED
@@ -17,7 +17,6 @@ spec/reports
17
17
  test/tmp
18
18
  test/version_tmp
19
19
  tmp
20
- .idea
21
20
  .ruby-version
22
21
  .rbenv-gemsets
23
22
  vendor/assets/javascripts/autonumeric_ujs.js.coffee
@@ -1,3 +1,7 @@
1
+ ### 1.9.43
2
+
3
+ - Update autoNumeric v 1.9.43
4
+
1
5
  ### 1.9.42
2
6
 
3
7
  - Update autoNumeric v 1.9.42
@@ -1,5 +1,5 @@
1
1
  module Autonumeric
2
2
  module Rails
3
- VERSION = '1.9.42'
3
+ VERSION = '1.9.43'
4
4
  end
5
5
  end
@@ -13,7 +13,7 @@
13
13
 
14
14
  ActiveRecord::Schema.define(version: 20131227002328) do
15
15
 
16
- create_table "records", force: true do |t|
16
+ create_table "records", force: :cascade do |t|
17
17
  t.decimal "field1", precision: 10, scale: 8
18
18
  t.decimal "field2", precision: 10, scale: 8
19
19
  end
@@ -0,0 +1,6 @@
1
+ def setup_dummy_library(lib)
2
+ path = Rails.root.join 'spec', 'dummy', 'app', 'assets', 'javascripts', 'application.js'
3
+ text = "//= require jquery\n//= require #{lib}\n"
4
+
5
+ File.open(path.to_s, 'w') { |io| io.write text }
6
+ end
@@ -2,7 +2,7 @@
2
2
  * autoNumeric.js
3
3
  * @author: Bob Knothe
4
4
  * @author: Sokolov Yura
5
- * @version: 1.9.42 - 2015-11-20 GMT 3:00 PM / 15:00
5
+ * @version: 1.9.43 - 2015-12-19 GMT 4:00 PM / 16:00
6
6
  *
7
7
  * Created by Robert J. Knothe on 2010-10-25. Please report any bugs to https://github.com/BobKnothe/autoNumeric
8
8
  * Contributor by Sokolov Yura on 2010-11-07
@@ -32,7 +32,18 @@
32
32
  * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
33
33
  * OTHER DEALINGS IN THE SOFTWARE.
34
34
  */
35
- (function ($) {
35
+ (function (factory) {
36
+ if (typeof define === "function" && define.amd) {
37
+ /** AMD. Register as an anonymous module. */
38
+ define(["jquery"], factory);
39
+ } else if (typeof module === "object" && module.exports) {
40
+ /** Node/CommonJS */
41
+ module.exports = factory(require("jquery"));
42
+ } else {
43
+ /** Browser globals */
44
+ factory(window.jQuery);
45
+ }
46
+ }(function ($) {
36
47
  "use strict";
37
48
  /*jslint browser: true*/
38
49
  /*global jQuery: false*/
@@ -42,6 +53,7 @@
42
53
  /**
43
54
  * Cross browser routine for getting selected range/cursor position
44
55
  */
56
+
45
57
  function getElementSelection(that) {
46
58
  var position = {};
47
59
  if (that.selectionStart === undefined) {
@@ -62,6 +74,7 @@
62
74
  /**
63
75
  * Cross browser routine for setting selected range/cursor position
64
76
  */
77
+
65
78
  function setElementSelection(that, start, end) {
66
79
  if (that.selectionStart === undefined) {
67
80
  that.focus();
@@ -82,6 +95,7 @@
82
95
  * - a function, which invoked with jQuery element, parameters and this parameter name and returns parameter value
83
96
  * - a name of function, attached to $(selector).autoNumeric.functionName(){} - which was called previously
84
97
  */
98
+
85
99
  function runCallbacks($this, settings) {
86
100
  /**
87
101
  * loops through the settings object (option array) to find the following
@@ -103,8 +117,9 @@
103
117
  /**
104
118
  * Converts the vMin, vMax & mDec string to numeric value
105
119
  */
120
+
106
121
  function convertKeyToNumber(settings, key) {
107
- if (typeof (settings[key]) === 'string') {
122
+ if (typeof(settings[key]) === 'string') {
108
123
  settings[key] *= 1;
109
124
  }
110
125
  }
@@ -113,6 +128,7 @@
113
128
  * Preparing user defined options for further usage
114
129
  * merge them with defaults appropriately
115
130
  */
131
+
116
132
  function autoCode($this, settings) {
117
133
  runCallbacks($this, settings);
118
134
  settings.tagList = ['b', 'caption', 'cite', 'code', 'dd', 'del', 'div', 'dfn', 'dt', 'em', 'h1', 'h2', 'h3', 'h4', 'h5', 'h6', 'ins', 'kdb', 'label', 'li', 'output', 'p', 'q', 's', 'sample', 'span', 'strong', 'td', 'th', 'u', 'var'];
@@ -159,6 +175,7 @@
159
175
  /**
160
176
  * strips all unwanted characters and leave only a number alert
161
177
  */
178
+
162
179
  function autoStrip(s, settings, strip_zero) {
163
180
  if (settings.aSign) { /** remove currency sign */
164
181
  while (s.indexOf(settings.aSign) > -1) {
@@ -198,6 +215,7 @@
198
215
  * places or removes brackets on negative values
199
216
  * works only when with pSign: 'p'
200
217
  */
218
+
201
219
  function negativeBracket(s, settings) {
202
220
  if (settings.pSign === 'p') {
203
221
  var brackets = settings.nBracket.split(',');
@@ -215,6 +233,7 @@
215
233
  /**
216
234
  * function to handle numbers less than 0 that are stored in Exponential notation ex: .0000001 stored as 1e-7
217
235
  */
236
+
218
237
  function checkValue(value, settings) {
219
238
  if (value) {
220
239
  var checkSmall = +value;
@@ -247,6 +266,7 @@
247
266
  /**
248
267
  * prepare number string to be converted to real number
249
268
  */
269
+
250
270
  function fixNumber(s, aDec, aNeg) {
251
271
  if (aDec && aDec !== '.') {
252
272
  s = s.replace(aDec, '.');
@@ -263,6 +283,7 @@
263
283
  /**
264
284
  * prepare real number to be converted to our format
265
285
  */
286
+
266
287
  function presentNumber(s, aDec, aNeg) {
267
288
  if (aNeg && aNeg !== '-') {
268
289
  s = s.replace('-', aNeg);
@@ -276,6 +297,7 @@
276
297
  /**
277
298
  * private function to check for empty value
278
299
  */
300
+
279
301
  function checkEmpty(iv, settings, signOnEmpty) {
280
302
  if (iv === '' || iv === settings.aNeg) {
281
303
  if (settings.wEmpty === 'zero') {
@@ -292,6 +314,7 @@
292
314
  /**
293
315
  * private function that formats our number
294
316
  */
317
+
295
318
  function autoGroup(iv, settings) {
296
319
  iv = autoStrip(iv, settings);
297
320
  var testNeg = iv.replace(',', '.'),
@@ -345,6 +368,7 @@
345
368
  * please note this handled as text - JavaScript math function can return inaccurate values
346
369
  * also this offers multiple rounding methods that are not easily accomplished in JavaScript
347
370
  */
371
+
348
372
  function autoRound(iv, settings) { /** value to string */
349
373
  iv = (iv === '') ? '0' : iv.toString();
350
374
  convertKeyToNumber(settings, 'mDec'); /** set mDec to number needed when mDec set by 'update method */
@@ -354,7 +378,7 @@
354
378
  var ivRounded = '',
355
379
  i = 0,
356
380
  nSign = '',
357
- rDec = (typeof (settings.aPad) === 'boolean' || settings.aPad === null) ? (settings.aPad ? settings.mDec : 0) : +settings.aPad;
381
+ rDec = (typeof(settings.aPad) === 'boolean' || settings.aPad === null) ? (settings.aPad ? settings.mDec : 0) : +settings.aPad;
358
382
  var truncateZeros = function (ivRounded) { /** truncate not needed zeros */
359
383
  var regex = (rDec === 0) ? (/(\.(?:\d*[1-9])?)0*$/) : rDec === 1 ? (/(\.\d(?:\d*[1-9])?)0*$/) : new RegExp('(\\.\\d{' + rDec + '}(?:\\d*[1-9])?)0*$');
360
384
  ivRounded = ivRounded.replace(regex, '$1'); /** If there are no decimal places, we don't need a decimal point at the end */
@@ -464,6 +488,7 @@
464
488
  /**
465
489
  * truncate decimal part of a number
466
490
  */
491
+
467
492
  function truncateDecimal(s, settings, paste) {
468
493
  var aDec = settings.aDec,
469
494
  mDec = settings.mDec;
@@ -489,6 +514,7 @@
489
514
  * and lays between settings.vMin and settings.vMax
490
515
  * and the string length does not exceed the digits in settings.vMin and settings.vMax
491
516
  */
517
+
492
518
  function autoCheck(s, settings) {
493
519
  s = autoStrip(s, settings);
494
520
  s = truncateDecimal(s, settings);
@@ -500,6 +526,7 @@
500
526
  /**
501
527
  * Holder object for field properties
502
528
  */
529
+
503
530
  function AutoNumericHolder(that, settings) {
504
531
  this.settings = settings;
505
532
  this.that = that;
@@ -862,6 +889,7 @@
862
889
  /**
863
890
  * thanks to Anthony & Evan C
864
891
  */
892
+
865
893
  function autoGet(obj) {
866
894
  if (typeof obj === 'string') {
867
895
  obj = obj.replace(/\[/g, "\\[").replace(/\]/g, "\\]");
@@ -876,6 +904,7 @@
876
904
  * function to attach data to the element
877
905
  * and imitate the holder
878
906
  */
907
+
879
908
  function getHolder($that, settings, update) {
880
909
  var data = $that.data('autoNumeric');
881
910
  if (!data) {
@@ -903,8 +932,10 @@
903
932
  init: function (options) {
904
933
  return this.each(function () {
905
934
  var $this = $(this),
906
- settings = $this.data('autoNumeric'), /** attempt to grab 'autoNumeric' settings, if they don't exist returns "undefined". */
907
- tagData = $this.data(), /** attempt to grab HTML5 data, if they don't exist we'll get "undefined".*/
935
+ settings = $this.data('autoNumeric'),
936
+ /** attempt to grab 'autoNumeric' settings, if they don't exist returns "undefined". */
937
+ tagData = $this.data(),
938
+ /** attempt to grab HTML5 data, if they don't exist we'll get "undefined".*/
908
939
  $input = $this.is('input[type=text], input[type=hidden], input[type=tel], input:not([type])');
909
940
  if (typeof settings !== 'object') { /** If we couldn't grab settings, create them from defaults and passed options. */
910
941
  settings = $.extend({}, $.fn.autoNumeric.defaults, tagData, options, {
@@ -1216,10 +1247,14 @@
1216
1247
  formParts = formFields.split('&'),
1217
1248
  formIndex = $('form').index($this),
1218
1249
  allFormElements = $('form:eq(' + formIndex + ')'),
1219
- aiIndex = [], /* all input index */
1220
- scIndex = [], /* successful control index */
1221
- rsubmitterTypes = /^(?:submit|button|image|reset|file)$/i, /* from jQuery serialize method */
1222
- rsubmittable = /^(?:input|select|textarea|keygen)/i, /* from jQuery serialize method */
1250
+ aiIndex = [],
1251
+ /* all input index */
1252
+ scIndex = [],
1253
+ /* successful control index */
1254
+ rsubmitterTypes = /^(?:submit|button|image|reset|file)$/i,
1255
+ /* from jQuery serialize method */
1256
+ rsubmittable = /^(?:input|select|textarea|keygen)/i,
1257
+ /* from jQuery serialize method */
1223
1258
  rcheckableType = /^(?:checkbox|radio)$/i,
1224
1259
  rnonAutoNumericTypes = /^(?:button|checkbox|color|date|datetime|datetime-local|email|file|image|month|number|password|radio|range|reset|search|submit|time|url|week)/i,
1225
1260
  count = 0;
@@ -1280,10 +1315,14 @@
1280
1315
  formFields = $this.serializeArray(),
1281
1316
  formIndex = $('form').index($this),
1282
1317
  allFormElements = $('form:eq(' + formIndex + ')'),
1283
- aiIndex = [], /* all input index */
1284
- scIndex = [], /* successful control index */
1285
- rsubmitterTypes = /^(?:submit|button|image|reset|file)$/i, /* from jQuery serialize method */
1286
- rsubmittable = /^(?:input|select|textarea|keygen)/i, /* from jQuery serialize method */
1318
+ aiIndex = [],
1319
+ /* all input index */
1320
+ scIndex = [],
1321
+ /* successful control index */
1322
+ rsubmitterTypes = /^(?:submit|button|image|reset|file)$/i,
1323
+ /* from jQuery serialize method */
1324
+ rsubmittable = /^(?:input|select|textarea|keygen)/i,
1325
+ /* from jQuery serialize method */
1287
1326
  rcheckableType = /^(?:checkbox|radio)$/i,
1288
1327
  rnonAutoNumericTypes = /^(?:button|checkbox|color|date|datetime|datetime-local|email|file|image|month|number|password|radio|range|reset|search|submit|time|url|week)/i,
1289
1328
  count = 0;
@@ -1462,4 +1501,4 @@
1462
1501
  */
1463
1502
  anDefault: null
1464
1503
  };
1465
- }(jQuery));
1504
+ }));
@@ -0,0 +1,2018 @@
1
+ /**
2
+ * autoNumeric.js
3
+ * @author: Bob Knothe
4
+ * @contributor: Sokolov Yura
5
+ * @version: 2.0-beta - 2015-12-19 GMT 4:00 PM / 16:00
6
+ *
7
+ * Created by Robert J. Knothe on 2009-08-09. Please report any bugs to https://github.com/BobKnothe/autoNumeric
8
+ *
9
+ * Copyright (c) 2009 Robert J. Knothe http://www.decorplanit.com/plugin/
10
+ *
11
+ * The MIT License (http://www.opensource.org/licenses/mit-license.php)
12
+ *
13
+ * Permission is hereby granted, free of charge, to any person
14
+ * obtaining a copy of this software and associated documentation
15
+ * files (the "Software"), to deal in the Software without
16
+ * restriction, including without limitation the rights to use,
17
+ * copy, modify, merge, publish, distribute, sub license, and/or sell
18
+ * copies of the Software, and to permit persons to whom the
19
+ * Software is furnished to do so, subject to the following
20
+ * conditions:
21
+ *
22
+ * The above copyright notice and this permission notice shall be
23
+ * included in all copies or substantial portions of the Software.
24
+ *
25
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
26
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
27
+ * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
28
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
29
+ * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
30
+ * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
31
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
32
+ * OTHER DEALINGS IN THE SOFTWARE.
33
+ */
34
+ (function (factory) {
35
+ if (typeof define === "function" && define.amd) {
36
+ /** AMD. Register as an anonymous module. */
37
+ define(["jquery"], factory);
38
+ } else if (typeof module === "object" && module.exports) {
39
+ /** Node/CommonJS */
40
+ module.exports = factory(require("jquery"));
41
+ } else {
42
+ /** Browser globals */
43
+ factory(window.jQuery);
44
+ }
45
+ }(function ($) {
46
+ "use strict";
47
+ /*jslint browser: true, bitwise: true*/
48
+ /*global jQuery: false, sessionStorage: false*/
49
+
50
+ /**
51
+ * Cross browser routine for getting selected range/cursor position
52
+ */
53
+ function getElementSelection(that) {
54
+ var position = {};
55
+ if (that.selectionStart === undefined) {
56
+ that.focus();
57
+ var select = document.selection.createRange();
58
+ position.length = select.text.length;
59
+ select.moveStart('character', -that.value.length);
60
+ position.end = select.text.length;
61
+ position.start = position.end - position.length;
62
+ } else {
63
+ position.start = that.selectionStart;
64
+ position.end = that.selectionEnd;
65
+ position.length = position.end - position.start;
66
+ }
67
+ return position;
68
+ }
69
+
70
+ /**
71
+ * Cross browser routine for setting selected range/cursor position
72
+ */
73
+ function setElementSelection(that, start, end) {
74
+ if (that.selectionStart === undefined) {
75
+ that.focus();
76
+ var r = that.createTextRange();
77
+ r.collapse(true);
78
+ r.moveEnd('character', end);
79
+ r.moveStart('character', start);
80
+ r.select();
81
+ } else {
82
+ that.selectionStart = start;
83
+ that.selectionEnd = end;
84
+ }
85
+ }
86
+
87
+ /**
88
+ * Function to handle errors messages
89
+ */
90
+ function throwErr(message, debug) {
91
+ if (debug) {
92
+ var err = new Error(message);
93
+ throw err;
94
+ }
95
+ }
96
+
97
+ /**
98
+ * run callbacks in parameters if any
99
+ * any parameter could be a callback:
100
+ * - a function, which invoked with jQuery element, parameters and this parameter name and returns parameter value
101
+ * - a name of function, attached to $(selector).autoNumeric.functionName(){} - which was called previously
102
+ */
103
+ function runCallbacks($this, settings) {
104
+ /**
105
+ * loops through the settings object (option array) to find the following
106
+ * k = option name example k=aNum
107
+ * val = option value example val=0123456789
108
+ */
109
+ $.each(settings, function (k, val) {
110
+ if (typeof val === 'function') {
111
+ settings[k] = val($this, settings, k);
112
+ } else if (typeof $this.autoNumeric[val] === 'function') {
113
+ /**
114
+ * calls the attached function from the html5 data example: data-a-sign="functionName"
115
+ */
116
+ settings[k] = $this.autoNumeric[val]($this, settings, k);
117
+ }
118
+ });
119
+ }
120
+
121
+ /**
122
+ * Preparing user defined options for further usage
123
+ * merge them with defaults appropriately
124
+ */
125
+ function autoCode($this, settings) {
126
+ runCallbacks($this, settings);
127
+ var vmax = settings.vMax.toString().split('.'),
128
+ vmin = (!settings.vMin && settings.vMin !== 0) ? [] : settings.vMin.toString().split('.');
129
+ settings.aNeg = settings.vMin < 0 ? '-' : '';
130
+ vmax[0] = vmax[0].replace('-', '');
131
+ vmin[0] = vmin[0].replace('-', '');
132
+ settings.mIntPos = Math.max(vmax[0].length, 1);
133
+ settings.mIntNeg = Math.max(vmin[0].length, 1);
134
+ if (settings.mDec === null) {
135
+ var vmaxLength = 0,
136
+ vminLength = 0;
137
+ if (vmax[1]) {
138
+ vmaxLength = vmax[1].length;
139
+ }
140
+ if (vmin[1]) {
141
+ vminLength = vmin[1].length;
142
+ }
143
+ settings.mDec = Math.max(vmaxLength, vminLength);
144
+ settings.oDec = settings.mDec;
145
+ } else {
146
+ settings.mDec = Number(settings.mDec);
147
+ }
148
+ /** set alternative decimal separator key */
149
+ if (settings.altDec === null && settings.mDec > 0) {
150
+ if (settings.aDec === '.' && settings.aSep !== ',') {
151
+ settings.altDec = ',';
152
+ } else if (settings.aDec === ',' && settings.aSep !== '.') {
153
+ settings.altDec = '.';
154
+ }
155
+ }
156
+ /** cache regexps for autoStrip */
157
+ var aNegReg = settings.aNeg ? '([-\\' + settings.aNeg + ']?)' : '(-?)';
158
+ settings.aNegRegAutoStrip = aNegReg;
159
+ settings.skipFirstAutoStrip = new RegExp(aNegReg + '[^-' + (settings.aNeg ? '\\' + settings.aNeg : '') + '\\' + settings.aDec + '\\d]' + '.*?(\\d|\\' + settings.aDec + '\\d)');
160
+ settings.skipLastAutoStrip = new RegExp('(\\d\\' + settings.aDec + '?)[^\\' + settings.aDec + '\\d]\\D*$');
161
+ var allowed = '-' + settings.aNum + '\\' + settings.aDec;
162
+ settings.allowedAutoStrip = new RegExp('[^' + allowed + ']', 'gi');
163
+ settings.numRegAutoStrip = new RegExp(aNegReg + '(?:\\' + settings.aDec + '?(\\d+\\' + settings.aDec + '\\d+)|(\\d*(?:\\' + settings.aDec + '\\d*)?))');
164
+ return settings;
165
+ }
166
+
167
+ /**
168
+ * strip all unwanted characters and leave only a number alert
169
+ */
170
+ function autoStrip(s, settings) {
171
+ if (settings.aSign !== '') { /** remove currency sign */
172
+ s = s.replace(settings.aSign, '');
173
+ }
174
+ if (settings.aSuffix) { /** remove suffix */
175
+ while (s.indexOf(settings.aSuffix) > -1) {
176
+ s = s.replace(settings.aSuffix, '');
177
+ }
178
+ }
179
+ s = s.replace(settings.skipFirstAutoStrip, '$1$2'); /** first replace anything before digits */
180
+ if ((settings.pNeg === 's' || (settings.pSign === 's' && settings.pNeg !== 'p')) && s.indexOf('-') > -1 && s !== '') {
181
+ settings.trailingNegative = true;
182
+ }
183
+ s = s.replace(settings.skipLastAutoStrip, '$1'); /** then replace anything after digits */
184
+ s = s.replace(settings.allowedAutoStrip, ''); /** then remove any uninterested characters */
185
+ if (settings.altDec) {
186
+ s = s.replace(settings.altDec, settings.aDec);
187
+ } /** get only number string */
188
+ var m = s.match(settings.numRegAutoStrip);
189
+ s = m ? [m[1], m[2], m[3]].join('') : '';
190
+ if (settings.lZero === 'allow' || settings.lZero === 'keep') {
191
+ var parts = [],
192
+ nSign = '';
193
+ parts = s.split(settings.aDec);
194
+ if (parts[0].indexOf(settings.aNeg) !== -1) {
195
+ nSign = settings.aNeg;
196
+ parts[0] = parts[0].replace(settings.aNeg, '');
197
+ }
198
+ if (nSign === "" && parts[0].length > settings.mIntPos && parts[0].charAt(0) === '0') { /** strip leading zero if need */
199
+ parts[0] = parts[0].slice(1);
200
+ }
201
+ if (nSign !== '' && parts[0].length > settings.mIntNeg && parts[0].charAt(0) === '0') { /** strip leading zero if need */
202
+ parts[0] = parts[0].slice(1);
203
+ }
204
+ s = nSign + parts.join(settings.aDec);
205
+ }
206
+ if ((settings.onOff && settings.lZero === 'deny') || (settings.lZero === 'allow' && settings.onOff === false)) {
207
+ var strip_reg = '^' + settings.aNegRegAutoStrip + '0*(\\d|$)';
208
+ strip_reg = new RegExp(strip_reg);
209
+ s = s.replace(strip_reg, '$1$2');
210
+ }
211
+ return s;
212
+ }
213
+
214
+ /**
215
+ * places or removes brackets on negative values
216
+ */
217
+ function negativeBracket(s, settings) {
218
+ if ((settings.pSign === 'p' && settings.pNeg === 'l') || (settings.pSign === 's' && settings.pNeg === 'p')) {
219
+ var brackets = settings.nBracket.split(',');
220
+ if (!settings.onOff) {
221
+ s = s.replace(settings.aNeg, '');
222
+ s = brackets[0] + s + brackets[1];
223
+ } else if (settings.onOff && s.charAt(0) === brackets[0]) {
224
+ s = s.replace(brackets[0], settings.aNeg);
225
+ s = s.replace(brackets[1], '');
226
+ }
227
+ }
228
+ return s;
229
+ }
230
+
231
+ /**
232
+ * convert locale format to javaSript numeric string
233
+ * allows locale decimal separator to be a period or comma - no thousand separator allowed of currency signs allowed
234
+ * '1234.56' OK
235
+ * '-1234.56' OK
236
+ * '1234.56-' OK
237
+ * '1234,56' OK
238
+ * '-1234,56' OK
239
+ * '1234,56-' OK
240
+ */
241
+ function convertLocale(s) {
242
+ s = s.replace(',', '.');
243
+ if (s.lastIndexOf('-') !== -1 && s.lastIndexOf('-') === s.length - 1) {
244
+ s = s.replace('-', '');
245
+ s = '-' + s;
246
+ }
247
+ return s;
248
+ }
249
+
250
+ /**
251
+ * prepare number string to be converted to real number
252
+ */
253
+ function fixNumber(s, aDec, aNeg) {
254
+ if (aDec && aDec !== '.') {
255
+ s = s.replace(aDec, '.');
256
+ }
257
+ if (aNeg && aNeg !== '-') {
258
+ s = s.replace(aNeg, '-');
259
+ }
260
+ if (!s.match(/\d/)) {
261
+ s += '0';
262
+ }
263
+ return s;
264
+ }
265
+
266
+ /**
267
+ * prepare real number to be converted to our format
268
+ */
269
+ function presentNumber(s, aDec, aNeg) {
270
+ if (aNeg && aNeg !== '-') {
271
+ s = s.replace('-', aNeg);
272
+ }
273
+ if (aDec && aDec !== '.') {
274
+ s = s.replace('.', aDec);
275
+ }
276
+ return s;
277
+ }
278
+
279
+ /**
280
+ * private function to check for empty value
281
+ */
282
+ function checkEmpty(iv, settings, signOnEmpty) {
283
+ if (iv === '' || iv === settings.aNeg) {
284
+ if (settings.wEmpty === 'always' || signOnEmpty) {
285
+ return (settings.pNeg === 'l') ? iv + settings.aSign + settings.aSuffix : settings.aSign + iv + settings.aSuffix;
286
+ }
287
+ return iv;
288
+ }
289
+ return null;
290
+ }
291
+
292
+ /**
293
+ * private function that formats our number
294
+ */
295
+ function autoGroup(iv, settings) {
296
+ iv = autoStrip(iv, settings);
297
+ if (settings.trailingNegative && iv.indexOf('-') === -1) {
298
+ iv = '-' + iv;
299
+ }
300
+ var empty = checkEmpty(iv, settings, true),
301
+ isNeg = iv.replace(',', '.') < 0;
302
+ if (iv.indexOf('-') > -1 && Number(iv) === 0) {
303
+ isNeg = true;
304
+ }
305
+ if (isNeg) {
306
+ iv = iv.replace('-', '');
307
+ }
308
+ if (empty !== null) {
309
+ return empty;
310
+ }
311
+ var digitalGroup = '';
312
+ settings.dGroup = settings.dGroup.toString();
313
+ if (settings.dGroup === '2') {
314
+ digitalGroup = /(\d)((\d)(\d{2}?)+)$/;
315
+ } else if (settings.dGroup === '2s') {
316
+ digitalGroup = /(\d)((?:\d{2}){0,2}\d{3}(?:(?:\d{2}){2}\d{3})*?)$/;
317
+ } else if (settings.dGroup === '4') {
318
+ digitalGroup = /(\d)((\d{4}?)+)$/;
319
+ } else {
320
+ digitalGroup = /(\d)((\d{3}?)+)$/;
321
+ } /** splits the string at the decimal string */
322
+ var ivSplit = iv.split(settings.aDec);
323
+ if (settings.altDec && ivSplit.length === 1) {
324
+ ivSplit = iv.split(settings.altDec);
325
+ } /** assigns the whole number to the a variable (s) */
326
+ var s = ivSplit[0];
327
+ if (settings.aSep !== '') {
328
+ while (digitalGroup.test(s)) { /** re-inserts the thousand separator via a regular expression */
329
+ s = s.replace(digitalGroup, '$1' + settings.aSep + '$2');
330
+ }
331
+ }
332
+ if (settings.mDec !== 0 && ivSplit.length > 1) {
333
+ if (ivSplit[1].length > settings.mDec) {
334
+ ivSplit[1] = ivSplit[1].substring(0, settings.mDec);
335
+ } /** joins the whole number with the decimal value */
336
+ iv = s + settings.aDec + ivSplit[1];
337
+ } else { /** if whole numbers only */
338
+ iv = s;
339
+ }
340
+ if (settings.pSign === 'p') {
341
+ if (isNeg && settings.pNeg === 'l') {
342
+ iv = settings.aNeg + settings.aSign + iv;
343
+ }
344
+ if (isNeg && settings.pNeg === 'r') {
345
+ iv = settings.aSign + settings.aNeg + iv;
346
+ }
347
+ if (isNeg && settings.pNeg === 's') {
348
+ iv = settings.aSign + iv + settings.aNeg;
349
+ }
350
+ if (!isNeg && !settings.trailingNegative) {
351
+ iv = settings.aSign + iv;
352
+ }
353
+ }
354
+ if (settings.pSign === 's') {
355
+ if (isNeg && settings.pNeg === 'r') {
356
+ iv = iv + settings.aSign + settings.aNeg;
357
+ }
358
+ if (isNeg && settings.pNeg === 'l') {
359
+ iv = iv + settings.aNeg + settings.aSign;
360
+ }
361
+ if (isNeg && settings.pNeg === 'p') {
362
+ iv = settings.aNeg + iv + settings.aSign;
363
+ }
364
+ if (!isNeg) {
365
+ iv = iv + settings.aSign;
366
+ }
367
+ }
368
+ if (settings.rawValue < 0 && settings.nBracket !== null) { /** removes the negative sign and places brackets */
369
+ iv = negativeBracket(iv, settings);
370
+ }
371
+ settings.trailingNegative = false;
372
+ return iv + settings.aSuffix;
373
+ }
374
+
375
+ /**
376
+ * round number after setting by pasting or $().autoNumericSet()
377
+ * private function for round the number
378
+ * please note this handled as text - JavaScript math function can return inaccurate values
379
+ * also this offers multiple rounding methods that are not easily accomplished in JavaScript
380
+ */
381
+ function autoRound(iv, settings) { /** value to string */
382
+ iv = (iv === '') ? '0' : iv.toString();
383
+ if (settings.mRound === 'N05' || settings.mRound === 'U05' || settings.mRound === 'D05') {
384
+ iv = (settings.mRound === 'N05') ? (Math.round(iv * 20) / 20).toString() : (settings.mRound === 'U05') ? (Math.ceil(iv * 20) / 20).toString() : (Math.floor(iv * 20) / 20).toString();
385
+ return (iv.indexOf('.') === -1) ? iv + '.00' : (iv.length - iv.indexOf('.') < 3) ? iv + '0' : iv;
386
+ }
387
+ var ivRounded = '',
388
+ i = 0,
389
+ nSign = '',
390
+ rDec = (typeof (settings.aPad) === 'boolean' || settings.aPad === null) ? (settings.aPad ? settings.mDec : 0) : Number(settings.aPad);
391
+ var truncateZeros = function (ivRounded) { /** truncate not needed zeros */
392
+ var regex = rDec === 0 ? (/(\.(?:\d*[1-9])?)0*$/) : rDec === 1 ? (/(\.\d(?:\d*[1-9])?)0*$/) : new RegExp('(\\.\\d{' + rDec + '}(?:\\d*[1-9])?)0*');
393
+ ivRounded = ivRounded.replace(regex, '$1'); /** If there are no decimal places, we don't need a decimal point at the end */
394
+ if (rDec === 0) {
395
+ ivRounded = ivRounded.replace(/\.$/, '');
396
+ }
397
+ return ivRounded;
398
+ };
399
+ if (iv.charAt(0) === '-') { /** Checks if the iv (input Value)is a negative value */
400
+ nSign = '-';
401
+ iv = iv.replace('-', ''); /** removes the negative sign will be added back later if required */
402
+ }
403
+ if (!iv.match(/^\d/)) { /** append a zero if first character is not a digit (then it is likely to be a dot)*/
404
+ iv = '0' + iv;
405
+ }
406
+ if (nSign === '-' && Number(iv) === 0) { /** determines if the value is zero - if zero no negative sign */
407
+ nSign = '';
408
+ }
409
+ if ((Number(iv) > 0 && settings.lZero !== 'keep') || (iv.length > 0 && settings.lZero === 'allow')) { /** trims leading zero's if needed */
410
+ iv = iv.replace(/^0*(\d)/, '$1');
411
+ }
412
+ var dPos = iv.lastIndexOf('.'),
413
+ /** virtual decimal position */
414
+ vdPos = (dPos === -1) ? iv.length - 1 : dPos,
415
+ /** checks decimal places to determine if rounding is required */
416
+ cDec = (iv.length - 1) - vdPos; /** check if no rounding is required */
417
+ if (cDec <= settings.mDec) {
418
+ ivRounded = iv; /** check if we need to pad with zeros */
419
+ if (cDec < rDec) {
420
+ if (dPos === -1) {
421
+ //ivRounded += '.';
422
+ ivRounded += settings.aDec;
423
+ }
424
+ var zeros = '000000';
425
+ while (cDec < rDec) {
426
+ zeros = zeros.substring(0, rDec - cDec);
427
+ ivRounded += zeros;
428
+ cDec += zeros.length;
429
+ }
430
+ } else if (cDec > rDec) {
431
+ ivRounded = truncateZeros(ivRounded);
432
+ } else if (cDec === 0 && rDec === 0) {
433
+ ivRounded = ivRounded.replace(/\.$/, '');
434
+ }
435
+ return (Number(ivRounded) === 0) ? ivRounded : nSign + ivRounded;
436
+ } /** rounded length of the string after rounding */
437
+ var rLength = dPos + settings.mDec,
438
+ tRound = Number(iv.charAt(rLength + 1)),
439
+ ivArray = iv.substring(0, rLength + 1).split(''),
440
+ odd = (iv.charAt(rLength) === '.') ? (iv.charAt(rLength - 1) % 2) : (iv.charAt(rLength) % 2);
441
+ /*jslint white: true*/
442
+ if ((tRound > 4 && settings.mRound === 'S') || /** Round half up symmetric */
443
+ (tRound > 4 && settings.mRound === 'A' && nSign === '') || /** Round half up asymmetric positive values */
444
+ (tRound > 5 && settings.mRound === 'A' && nSign === '-') || /** Round half up asymmetric negative values */
445
+ (tRound > 5 && settings.mRound === 's') || /** Round half down symmetric */
446
+ (tRound > 5 && settings.mRound === 'a' && nSign === '') || /** Round half down asymmetric positive values */
447
+ (tRound > 4 && settings.mRound === 'a' && nSign === '-') || /** Round half down asymmetric negative values */
448
+ (tRound > 5 && settings.mRound === 'B') || /** Round half even "Banker's Rounding" */
449
+ (tRound === 5 && settings.mRound === 'B' && odd === 1) || /** Round half even "Banker's Rounding" */
450
+ (tRound > 0 && settings.mRound === 'C' && nSign === '') || /** Round to ceiling toward positive infinite */
451
+ (tRound > 0 && settings.mRound === 'F' && nSign === '-') || /** Round to floor toward negative infinite */
452
+ (tRound > 0 && settings.mRound === 'U')) { /** Round up away from zero */
453
+ /*jslint white: false*/
454
+ for (i = (ivArray.length - 1); i >= 0; i -= 1) { /** Round up the last digit if required, and continue until no more 9's are found */
455
+ if (ivArray[i] !== '.') {
456
+ ivArray[i] = +ivArray[i] + 1;
457
+ if (ivArray[i] < 10) {
458
+ break;
459
+ }
460
+ if (i > 0) {
461
+ ivArray[i] = '0';
462
+ }
463
+ }
464
+ }
465
+ }
466
+ ivArray = ivArray.slice(0, rLength + 1); /** Reconstruct the string, converting any 10's to 0's */
467
+ ivRounded = truncateZeros(ivArray.join('')); /** return rounded value */
468
+ return (Number(ivRounded) === 0) ? ivRounded : nSign + ivRounded;
469
+ }
470
+
471
+ /**
472
+ * truncate decimal part of a number
473
+ */
474
+ function truncateDecimal(s, settings, paste) {
475
+ var aDec = settings.aDec,
476
+ mDec = settings.mDec;
477
+ s = (paste === 'paste') ? autoRound(s, settings) : s;
478
+ if (aDec && mDec) {
479
+ var parts = s.split(aDec);
480
+ /** truncate decimal part to satisfying length
481
+ * cause we would round it anyway */
482
+ if (parts[1] && parts[1].length > mDec) {
483
+ if (mDec > 0) {
484
+ parts[1] = parts[1].substring(0, mDec);
485
+ s = parts.join(aDec);
486
+ } else {
487
+ s = parts[0];
488
+ }
489
+ }
490
+ }
491
+ return s;
492
+ }
493
+
494
+ /**
495
+ * Function to parse vMin, vMax & the input value to prepare for testing to determine if the value falls within the min / max range
496
+ * Return an object example: vMin: "999999999999999.99" returns the following "{s: -1, e: 12, c: Array[15]}"
497
+ * This function is adapted from Big.js https://github.com/MikeMcl/big.js/
498
+ * Many thanks to Mike
499
+ */
500
+ function parseStr(n) {
501
+ var x = {},
502
+ e,
503
+ i,
504
+ nL,
505
+ j;
506
+ /** Minus zero? */
507
+ if (n === 0 && 1 / n < 0) {
508
+ n = '-0';
509
+ }
510
+ /** Determine sign. 1 positive, -1 negative */
511
+ if (n.charAt(0) === '-') {
512
+ n = n.slice(1);
513
+ x.s = -1;
514
+ } else {
515
+ x.s = 1;
516
+ }
517
+ /** Decimal point? */
518
+ e = n.indexOf('.');
519
+ if (e > -1) {
520
+ n = n.replace('.', '');
521
+ }
522
+ /** length of string if no decimal character */
523
+ if (e < 0) {
524
+ /** Integer. */
525
+ e = n.length;
526
+ }
527
+ /** Determine leading zeros. */
528
+ i = (n.search(/[1-9]/i) === -1) ? n.length : n.search(/[1-9]/i);
529
+ nL = n.length;
530
+ if (i === nL) {
531
+ /** Zero. */
532
+ x.e = 0;
533
+ x.c = [0];
534
+ } else {
535
+ /** Determine trailing zeros. */
536
+ for (j = nL - 1; n.charAt(j) === '0'; j -= 1) {
537
+ nL -= 1;
538
+ }
539
+ nL -= 1;
540
+ /** Decimal location. */
541
+ x.e = e - i - 1;
542
+ x.c = [];
543
+ /** Convert string to array of digits without leading/trailing zeros. */
544
+ for (e = 0; i <= nL; i += 1) {
545
+ x.c[e] = +n.charAt(i);
546
+ e += 1;
547
+ }
548
+ }
549
+ return x;
550
+ }
551
+
552
+ /**
553
+ * Function to test if the input value falls with the Min / Max settings
554
+ * This uses the parsed strings for the above parseStr function
555
+ * This function is adapted from Big.js https://github.com/MikeMcl/big.js/
556
+ * Many thanks to Mike
557
+ */
558
+ function testMinMax(y, x) {
559
+ var xNeg,
560
+ xc = x.c,
561
+ yc = y.c,
562
+ i = x.s,
563
+ j = y.s,
564
+ k = x.e,
565
+ l = y.e;
566
+ /** Either zero? */
567
+ if (!xc[0] || !yc[0]) {
568
+ return !xc[0] ? !yc[0] ? 0 : -j : i;
569
+ }
570
+ /** Signs differ? */
571
+ if (i !== j) {
572
+ return i;
573
+ }
574
+ xNeg = i < 0;
575
+ /** Compare exponents. */
576
+ if (k !== l) {
577
+ return k > l ^ xNeg ? 1 : -1;
578
+ }
579
+ i = -1;
580
+ k = xc.length;
581
+ l = yc.length;
582
+ j = (k < l) ? k : l;
583
+ /** Compare digit by digit. */
584
+ for (i += 1; i < j; i += 1) {
585
+ if (xc[i] !== yc[i]) {
586
+ return xc[i] > yc[i] ^ xNeg ? 1 : -1;
587
+ }
588
+ }
589
+ /** Compare lengths */
590
+ return k === l ? 0 : k > l ^ xNeg ? 1 : -1;
591
+ }
592
+
593
+ /**
594
+ * checking that number satisfy format conditions
595
+ * and lays between settings.vMin and settings.vMax
596
+ * and the string length does not exceed the digits in settings.vMin and settings.vMax
597
+ */
598
+ function autoCheck(s, settings) {
599
+ s = s.replace(',', '.');
600
+ var minParse = parseStr(settings.vMin),
601
+ maxParse = parseStr(settings.vMax),
602
+ valParse = parseStr(s);
603
+ return testMinMax(minParse, valParse) > -1 && testMinMax(maxParse, valParse) < 1;
604
+ }
605
+
606
+ /**
607
+ * Holder object for field properties
608
+ */
609
+ function AutoNumericHolder(that, settings) {
610
+ this.settings = settings;
611
+ this.that = that;
612
+ this.$that = $(that);
613
+ this.formatted = false;
614
+ this.settingsClone = autoCode(this.$that, this.settings);
615
+ this.value = that.value;
616
+ }
617
+ AutoNumericHolder.prototype = {
618
+ init: function (e) {
619
+ this.value = this.that.value;
620
+ this.settingsClone = autoCode(this.$that, this.settings);
621
+ this.ctrlKey = e.ctrlKey;
622
+ this.cmdKey = e.metaKey;
623
+ this.shiftKey = e.shiftKey;
624
+ this.selection = getElementSelection(this.that); /** keypress event overwrites meaningful value of e.keyCode */
625
+ if (e.type === 'keydown' || e.type === 'keyup') {
626
+ this.kdCode = e.keyCode;
627
+ }
628
+ this.which = e.which;
629
+ this.processed = false;
630
+ this.formatted = false;
631
+ },
632
+ setSelection: function (start, end, setReal) {
633
+ start = Math.max(start, 0);
634
+ end = Math.min(end, this.that.value.length);
635
+ this.selection = {
636
+ start: start,
637
+ end: end,
638
+ length: end - start
639
+ };
640
+ if (setReal === undefined || setReal) {
641
+ setElementSelection(this.that, start, end);
642
+ }
643
+ },
644
+ setPosition: function (pos, setReal) {
645
+ this.setSelection(pos, pos, setReal);
646
+ },
647
+ getBeforeAfter: function () {
648
+ var value = this.value,
649
+ left = value.substring(0, this.selection.start),
650
+ right = value.substring(this.selection.end, value.length);
651
+ return [left, right];
652
+ },
653
+ getBeforeAfterStriped: function () {
654
+ var settingsClone = this.settingsClone,
655
+ parts = this.getBeforeAfter();
656
+ parts[0] = autoStrip(parts[0], this.settingsClone);
657
+ parts[1] = autoStrip(parts[1], this.settingsClone);
658
+ if (settingsClone.trailingNegative && parts[0].indexOf('-') === -1) {
659
+ parts[0] = '-' + parts[0];
660
+ parts[1] = (parts[1] === '-') ? '' : parts[1];
661
+ }
662
+ settingsClone.trailingNegative = false;
663
+ return parts;
664
+ },
665
+
666
+ /**
667
+ * strip parts from excess characters and leading zeroes
668
+ */
669
+ normalizeParts: function (left, right) {
670
+ var settingsClone = this.settingsClone;
671
+ left = autoStrip(left, settingsClone); /** prevents multiple leading zeros from being entered */
672
+ right = autoStrip(right, settingsClone); /** if right is not empty and first character is not aDec, */
673
+ if (settingsClone.trailingNegative && left.indexOf('-') === -1) {
674
+ left = '-' + left;
675
+ settingsClone.trailingNegative = false;
676
+ }
677
+ if ((left === '' || left === settingsClone.aNeg) && settingsClone.lZero === 'deny') {
678
+ if (right > '') {
679
+ right = right.replace(/^0*(\d)/, '$1');
680
+ }
681
+ }
682
+ var new_value = left + right; /** insert zero if has leading dot */
683
+ if (settingsClone.aDec) {
684
+ var m = new_value.match(new RegExp('^' + settingsClone.aNegRegAutoStrip + '\\' + settingsClone.aDec));
685
+ if (m) {
686
+ left = left.replace(m[1], m[1] + '0');
687
+ new_value = left + right;
688
+ }
689
+ }
690
+ return [left, right];
691
+ },
692
+
693
+ /**
694
+ * set part of number to value keeping position of cursor
695
+ */
696
+ setValueParts: function (left, right, paste) {
697
+ var settingsClone = this.settingsClone,
698
+ parts = this.normalizeParts(left, right),
699
+ new_value = parts.join(''),
700
+ position = parts[0].length;
701
+ if (autoCheck(new_value, settingsClone)) {
702
+ new_value = truncateDecimal(new_value, settingsClone, paste);
703
+ var test_value = (new_value.indexOf(',') !== -1) ? new_value.replace(',', '.') : new_value,
704
+ text_value = test_value;
705
+ if (test_value === '' || test_value === settingsClone.aNeg) {
706
+ settingsClone.rawValue = '';
707
+ } else {
708
+ settingsClone.rawValue = text_value;
709
+ }
710
+ if (position > new_value.length) {
711
+ position = new_value.length;
712
+ }
713
+ this.value = new_value;
714
+ this.setPosition(position, false);
715
+ return true;
716
+ }
717
+ return false;
718
+ },
719
+
720
+ /**
721
+ * helper function for expandSelectionOnSign
722
+ * returns sign position of a formatted value
723
+ */
724
+ signPosition: function () {
725
+ var settingsClone = this.settingsClone,
726
+ aSign = settingsClone.aSign,
727
+ that = this.that;
728
+ if (aSign) {
729
+ var aSignLen = aSign.length;
730
+ if (settingsClone.pSign === 'p') {
731
+ var hasNeg = settingsClone.aNeg && that.value && that.value.charAt(0) === settingsClone.aNeg;
732
+ return hasNeg ? [1, aSignLen + 1] : [0, aSignLen];
733
+ }
734
+ var valueLen = that.value.length;
735
+ return [valueLen - aSignLen, valueLen];
736
+ }
737
+ return [1000, -1];
738
+ },
739
+
740
+ /**
741
+ * expands selection to cover whole sign
742
+ * prevents partial deletion/copying/overwriting of a sign
743
+ */
744
+ expandSelectionOnSign: function (setReal) {
745
+ var sign_position = this.signPosition(),
746
+ selection = this.selection;
747
+ if (selection.start < sign_position[1] && selection.end > sign_position[0]) { /** if selection catches something except sign and catches only space from sign */
748
+ if ((selection.start < sign_position[0] || selection.end > sign_position[1]) && this.value.substring(Math.max(selection.start, sign_position[0]), Math.min(selection.end, sign_position[1])).match(/^\s*$/)) { /** then select without empty space */
749
+ if (selection.start < sign_position[0]) {
750
+ this.setSelection(selection.start, sign_position[0], setReal);
751
+ } else {
752
+ this.setSelection(sign_position[1], selection.end, setReal);
753
+ }
754
+ } else { /** else select with whole sign */
755
+ this.setSelection(Math.min(selection.start, sign_position[0]), Math.max(selection.end, sign_position[1]), setReal);
756
+ }
757
+ }
758
+ },
759
+
760
+ /**
761
+ * try to strip pasted value to digits
762
+ */
763
+ checkPaste: function () {
764
+ if (this.valuePartsBeforePaste !== undefined) {
765
+ var parts = this.getBeforeAfter(),
766
+ oldParts = this.valuePartsBeforePaste;
767
+ delete this.valuePartsBeforePaste; /** try to strip pasted value first */
768
+ parts[0] = parts[0].substr(0, oldParts[0].length) + autoStrip(parts[0].substr(oldParts[0].length), this.settingsClone);
769
+ if (!this.setValueParts(parts[0], parts[1], 'paste')) {
770
+ this.value = oldParts.join('');
771
+ this.setPosition(oldParts[0].length, false);
772
+ }
773
+ }
774
+ },
775
+
776
+ /**
777
+ * process pasting, cursor moving and skipping of not interesting keys
778
+ * if returns true, further processing is not performed
779
+ */
780
+ skipAllways: function (e) {
781
+ var kdCode = this.kdCode,
782
+ which = this.which,
783
+ ctrlKey = this.ctrlKey,
784
+ cmdKey = this.cmdKey,
785
+ shiftKey = this.shiftKey; /** catch the ctrl up on ctrl-v */
786
+ if (((ctrlKey || cmdKey) && e.type === 'keyup' && this.valuePartsBeforePaste !== undefined) || (shiftKey && kdCode === 45)) {
787
+ this.checkPaste();
788
+ return false;
789
+ }
790
+ /** codes are taken from http://www.cambiaresearch.com/c4/702b8cd1-e5b0-42e6-83ac-25f0306e3e25/Javascript-Char-Codes-Key-Codes.aspx
791
+ * skip Fx keys, windows keys, other special keys
792
+ */
793
+ if ((kdCode >= 112 && kdCode <= 123) || (kdCode >= 91 && kdCode <= 93) || (kdCode >= 9 && kdCode <= 31) || (kdCode < 8 && (which === 0 || which === kdCode)) || kdCode === 144 || kdCode === 145 || kdCode === 45 || kdCode === 224) {
794
+ return true;
795
+ }
796
+ if ((ctrlKey || cmdKey) && kdCode === 65) { /** if select all (a=65)*/
797
+ if (this.settings.sNumber) {
798
+ e.preventDefault();
799
+ var valueLen = this.that.value.length,
800
+ aSignLen = this.settings.aSign.length,
801
+ negLen = (this.that.value.indexOf('-') === -1) ? 0 : 1,
802
+ aSuffixLen = this.settings.aSuffix.length,
803
+ pSign = this.settings.pSign,
804
+ pNeg = this.settings.pNeg,
805
+ start = (pSign === 's') ? 0 : (pNeg === 'l' && negLen === 1 && aSignLen > 0) ? aSignLen + 1 : aSignLen,
806
+ end = (pSign === 'p') ? valueLen - aSuffixLen : (pNeg === 'l') ? valueLen - (aSuffixLen + aSignLen) : (pNeg === 'r') ? (aSignLen > 0) ? valueLen - (aSignLen + negLen + aSuffixLen) : valueLen - (aSignLen + aSuffixLen) : valueLen - (aSignLen + aSuffixLen);
807
+ setElementSelection(this.that, start, end);
808
+ }
809
+ return true;
810
+ }
811
+ if ((ctrlKey || cmdKey) && (kdCode === 67 || kdCode === 86 || kdCode === 88)) { /** if copy (c=67) paste (v=86) or cut (x=88) */
812
+ if (e.type === 'keydown') {
813
+ this.expandSelectionOnSign();
814
+ }
815
+ if (kdCode === 86 || kdCode === 45) { /** try to prevent wrong paste */
816
+ if (e.type === 'keydown' || e.type === 'keypress') {
817
+ if (this.valuePartsBeforePaste === undefined) {
818
+ this.valuePartsBeforePaste = this.getBeforeAfter();
819
+ }
820
+ } else {
821
+ this.checkPaste();
822
+ }
823
+ }
824
+ return e.type === 'keydown' || e.type === 'keypress' || kdCode === 67;
825
+ }
826
+ if (ctrlKey || cmdKey) {
827
+ return true;
828
+ }
829
+ if (kdCode === 37 || kdCode === 39) { /** jump over thousand separator */
830
+ var aSep = this.settingsClone.aSep,
831
+ aDec = this.settingsClone.aDec,
832
+ startJump = this.selection.start,
833
+ value = this.that.value;
834
+ if (e.type === 'keydown' && !this.shiftKey) {
835
+ if (kdCode === 37 && (value.charAt(startJump - 2) === aSep || value.charAt(startJump - 2) === aDec)) {
836
+ this.setPosition(startJump - 1);
837
+ } else if (kdCode === 39 && (value.charAt(startJump + 1) === aSep || value.charAt(startJump + 1) === aDec)) {
838
+ this.setPosition(startJump + 1);
839
+ }
840
+ }
841
+ return true;
842
+ }
843
+ if (kdCode >= 34 && kdCode <= 40) {
844
+ return true;
845
+ }
846
+ return false;
847
+ },
848
+
849
+ /**
850
+ * process deletion of characters when the minus sign is to the right of the numeric characters
851
+ */
852
+ processTrailing: function (parts) {
853
+ var settingsClone = this.settingsClone;
854
+ if (settingsClone.pSign === 'p' && settingsClone.pNeg === 's') {
855
+ if (this.kdCode === 8) {
856
+ settingsClone.caretFix = (this.selection.start >= this.value.indexOf(settingsClone.aSuffix) && settingsClone.aSuffix !== '') ? true : false;
857
+ if (this.value.charAt(this.selection.start - 1) === '-') {
858
+ parts[0] = parts[0].substring(1);
859
+ } else if (this.selection.start <= this.value.length - settingsClone.aSuffix.length) {
860
+ parts[0] = parts[0].substring(0, parts[0].length - 1);
861
+ }
862
+ } else {
863
+ settingsClone.caretFix = (this.selection.start >= this.value.indexOf(settingsClone.aSuffix) && settingsClone.aSuffix !== '') ? true : false;
864
+ if (this.selection.start >= this.value.indexOf(settingsClone.aSign) + settingsClone.aSign.length) {
865
+ parts[1] = parts[1].substring(1, parts[1].length);
866
+ }
867
+ if (parts[0].indexOf('-') > -1 && this.value.charAt(this.selection.start) === '-') {
868
+ parts[0] = parts[0].substring(1);
869
+ }
870
+ }
871
+ }
872
+ if (settingsClone.pSign === 's' && settingsClone.pNeg === 'l') {
873
+ settingsClone.caretFix = (this.selection.start >= this.value.indexOf(settingsClone.aNeg) + settingsClone.aNeg.length) ? true : false;
874
+ if (this.kdCode === 8) {
875
+ if (this.selection.start === (this.value.indexOf(settingsClone.aNeg) + settingsClone.aNeg.length) && this.value.indexOf(settingsClone.aNeg) !== -1) {
876
+ parts[0] = parts[0].substring(1);
877
+ } else if (parts[0] !== '-' && ((this.selection.start <= this.value.indexOf(settingsClone.aNeg)) || this.value.indexOf(settingsClone.aNeg) === -1)) {
878
+ parts[0] = parts[0].substring(0, parts[0].length - 1);
879
+ }
880
+ } else {
881
+ if (parts[0][0] === '-') {
882
+ parts[1] = parts[1].substring(1);
883
+ }
884
+ if (this.selection.start === this.value.indexOf(settingsClone.aNeg) && this.value.indexOf(settingsClone.aNeg) !== -1) {
885
+ parts[0] = parts[0].substring(1);
886
+ }
887
+ }
888
+ }
889
+ if (settingsClone.pSign === 's' && settingsClone.pNeg === 'r') {
890
+ settingsClone.caretFix = (this.selection.start >= this.value.indexOf(settingsClone.aNeg) + settingsClone.aNeg.length) ? true : false;
891
+ if (this.kdCode === 8) {
892
+ if (this.selection.start === (this.value.indexOf(settingsClone.aNeg) + settingsClone.aNeg.length)) {
893
+ parts[0] = parts[0].substring(1);
894
+ } else if (parts[0] !== '-' && this.selection.start <= (this.value.indexOf(settingsClone.aNeg) - settingsClone.aSign.length)) {
895
+ parts[0] = parts[0].substring(0, parts[0].length - 1);
896
+ } else if (parts[0] !== '' && this.value.indexOf(settingsClone.aNeg) === -1) {
897
+ parts[0] = parts[0].substring(0, parts[0].length - 1);
898
+ }
899
+ } else {
900
+ settingsClone.caretFix = (this.selection.start >= this.value.indexOf(settingsClone.aSign) && settingsClone.aSign !== '') ? true : false;
901
+ if (this.selection.start === this.value.indexOf(settingsClone.aNeg)) {
902
+ parts[0] = parts[0].substring(1);
903
+ }
904
+ parts[1] = parts[1].substring(1);
905
+ }
906
+ }
907
+ return parts;
908
+ },
909
+
910
+ /**
911
+ * process deletion of characters
912
+ * returns true if processing performed
913
+ */
914
+ processAllways: function () {
915
+ var settingsClone = this.settingsClone,
916
+ parts = [];
917
+ if (this.kdCode === 8 || this.kdCode === 46) {
918
+ if (!this.selection.length) {
919
+ parts = this.getBeforeAfterStriped();
920
+ if (parts[0] === '' && parts[1] === '') {
921
+ settingsClone.throwInput = false;
922
+ }
923
+ if ((settingsClone.pSign === 'p' && settingsClone.pNeg === 's') || (settingsClone.pSign === 's' && settingsClone.pNeg !== 'p')) {
924
+ parts = this.processTrailing(parts);
925
+ } else {
926
+ if (this.kdCode === 8) {
927
+ parts[0] = parts[0].substring(0, parts[0].length - 1);
928
+ } else {
929
+ parts[1] = parts[1].substring(1, parts[1].length);
930
+ }
931
+ }
932
+ this.setValueParts(parts[0], parts[1]);
933
+ } else {
934
+ this.expandSelectionOnSign(false);
935
+ parts = this.getBeforeAfterStriped();
936
+ this.setValueParts(parts[0], parts[1]);
937
+ }
938
+ return true;
939
+ }
940
+ return false;
941
+ },
942
+
943
+ /**
944
+ * process insertion of characters
945
+ * returns true if processing performed
946
+ */
947
+ processKeypress: function () {
948
+ var settingsClone = this.settingsClone,
949
+ cCode = String.fromCharCode(this.which),
950
+ parts = this.getBeforeAfterStriped(),
951
+ left = parts[0],
952
+ right = parts[1];
953
+ settingsClone.throwInput = true;
954
+ /** start rules when the decimal character key is pressed always use numeric pad dot to insert decimal separator */
955
+ if (cCode === settingsClone.aDec || (settingsClone.altDec && cCode === settingsClone.altDec) || ((cCode === '.' || cCode === ',') && this.kdCode === 110)) { /** do not allow decimal character if no decimal part allowed */
956
+ if (!settingsClone.mDec || !settingsClone.aDec) {
957
+ return true;
958
+ } /** do not allow decimal character before aNeg character */
959
+ if (settingsClone.aNeg && right.indexOf(settingsClone.aNeg) > -1) {
960
+ return true;
961
+ } /** do not allow decimal character if other decimal character present */
962
+ if (left.indexOf(settingsClone.aDec) > -1) {
963
+ return true;
964
+ }
965
+ if (right.indexOf(settingsClone.aDec) > 0) {
966
+ return true;
967
+ }
968
+ if (right.indexOf(settingsClone.aDec) === 0) {
969
+ right = right.substr(1);
970
+ }
971
+ this.setValueParts(left + settingsClone.aDec, right, null);
972
+ return true;
973
+ }
974
+ if (cCode === '-' || cCode === '+') { /** prevent minus if not allowed */
975
+ if (!settingsClone) {
976
+ return true;
977
+ } /** caret is always after minus */
978
+ if ((settingsClone.pSign === 'p' && settingsClone.pNeg === 's') || (settingsClone.pSign === 's' && settingsClone.pNeg !== 'p')) {
979
+ if (left === '' && right.indexOf(settingsClone.aNeg) > -1) {
980
+ left = settingsClone.aNeg;
981
+ right = right.substring(1, right.length);
982
+ } /** change sign of number, remove part if should */
983
+ if (left.charAt(0) === '-' || left.indexOf(settingsClone.aNeg) !== -1) {
984
+ left = left.substring(1, left.length);
985
+ } else {
986
+ left = (cCode === '-') ? settingsClone.aNeg + left : left;
987
+ }
988
+ } else {
989
+ if (left === '' && right.indexOf(settingsClone.aNeg) > -1) {
990
+ left = settingsClone.aNeg;
991
+ right = right.substring(1, right.length);
992
+ } /** change sign of number, remove part if should */
993
+ if (left.charAt(0) === settingsClone.aNeg) {
994
+ left = left.substring(1, left.length);
995
+ } else {
996
+ left = (cCode === '-') ? settingsClone.aNeg + left : left;
997
+ }
998
+ }
999
+ this.setValueParts(left, right, null);
1000
+ return true;
1001
+ }
1002
+ if (cCode >= '0' && cCode <= '9') { /** if try to insert digit before minus */
1003
+ if (settingsClone.aNeg && left === '' && right.indexOf(settingsClone.aNeg) > -1) {
1004
+ left = settingsClone.aNeg;
1005
+ right = right.substring(1, right.length);
1006
+ }
1007
+ if (settingsClone.vMax <= 0 && settingsClone.vMin < settingsClone.vMax && this.value.indexOf(settingsClone.aNeg) === -1 && cCode !== '0') {
1008
+ left = settingsClone.aNeg + left;
1009
+ }
1010
+ this.setValueParts(left + cCode, right, null);
1011
+ return true;
1012
+ } /** prevent any other character */
1013
+ settingsClone.throwInput = false;
1014
+ return true;
1015
+ },
1016
+
1017
+ /**
1018
+ * formatting of just processed value with keeping of cursor position
1019
+ */
1020
+ formatQuick: function (e) {
1021
+ var settingsClone = this.settingsClone,
1022
+ parts = this.getBeforeAfterStriped(),
1023
+ leftLength = this.value,
1024
+ kuCode = e.keyCode;
1025
+ /** no grouping separator and no currency sign */
1026
+ if ((settingsClone.aSep === '' || (settingsClone.aSep !== '' && leftLength.indexOf(settingsClone.aSep) === -1)) && (settingsClone.aSign === '' || (settingsClone.aSign !== '' && leftLength.indexOf(settingsClone.aSign) === -1))) {
1027
+ var subParts = [],
1028
+ nSign = '';
1029
+ subParts = leftLength.split(settingsClone.aDec);
1030
+ if (subParts[0].indexOf('-') > -1) {
1031
+ nSign = '-';
1032
+ subParts[0] = subParts[0].replace('-', '');
1033
+ parts[0] = parts[0].replace('-', '');
1034
+ }
1035
+ if (nSign === '' && subParts[0].length > settingsClone.mIntPos && parts[0].charAt(0) === '0') { /** strip leading zero on positive value if need */
1036
+ parts[0] = parts[0].slice(1);
1037
+ }
1038
+ if (nSign === '-' && subParts[0].length > settingsClone.mIntNeg && parts[0].charAt(0) === '0') { /** strip leading zero on negative value if need */
1039
+ parts[0] = parts[0].slice(1);
1040
+ }
1041
+ parts[0] = nSign + parts[0];
1042
+ }
1043
+ var value = autoGroup(this.value, this.settingsClone);
1044
+ var position = value.length;
1045
+ if (value) {
1046
+ /** prepare regexp which searches for cursor position from unformatted left part */
1047
+ var left_ar = parts[0].split(''),
1048
+ i = 0;
1049
+ /** fixes caret position with trailing minus sign */
1050
+ if ((settingsClone.pNeg === 's' || (settingsClone.pSign === 's' && settingsClone.pNeg !== 'p')) && left_ar[0] === '-' && settingsClone.aNeg !== '') {
1051
+ left_ar.shift();
1052
+ if (settingsClone.pSign === 's' && settingsClone.pNeg === 'l' && (kuCode === 8 || this.kdCode === 8 || kuCode === 46 || this.kdCode === 46) && settingsClone.caretFix) {
1053
+ left_ar.push('-');
1054
+ settingsClone.caretFix = (e.type === 'keydown') ? true : false;
1055
+ }
1056
+ if (settingsClone.pSign === 'p' && settingsClone.pNeg === 's' && (kuCode === 8 || this.kdCode === 8 || kuCode === 46 || this.kdCode === 46) && settingsClone.caretFix) {
1057
+ left_ar.push('-');
1058
+ settingsClone.caretFix = (e.type === 'keydown') ? true : false;
1059
+ }
1060
+ if (settingsClone.pSign === 's' && settingsClone.pNeg === 'r' && (kuCode === 8 || this.kdCode === 8 || kuCode === 46 || this.kdCode === 46) && settingsClone.caretFix) {
1061
+ var signParts = settingsClone.aSign.split(''),
1062
+ escapeChr = ['\\', '^', '$', '.', '|', '?', '*', '+', '(', ')', '['],
1063
+ escapedParts = [],
1064
+ escapedSign = '';
1065
+ $.each(signParts, function (i, miniParts) {
1066
+ miniParts = signParts[i];
1067
+ if ($.inArray(miniParts, escapeChr) !== -1) {
1068
+ escapedParts.push('\\' + miniParts);
1069
+ } else {
1070
+ escapedParts.push(miniParts);
1071
+ }
1072
+ });
1073
+ if (kuCode === 8 || this.kdCode === 8) {
1074
+ escapedParts.push('-');
1075
+ }
1076
+ escapedSign = escapedParts.join('');
1077
+ left_ar.push(escapedSign);
1078
+ settingsClone.caretFix = (e.type === 'keydown') ? true : false;
1079
+ }
1080
+ }
1081
+ for (i; i < left_ar.length; i += 1) { /** thanks Peter Kovari */
1082
+ if (!left_ar[i].match('\\d')) {
1083
+ left_ar[i] = '\\' + left_ar[i];
1084
+ }
1085
+ }
1086
+ var leftReg = new RegExp('^.*?' + left_ar.join('.*?')),
1087
+ newLeft = value.match(leftReg); /** search cursor position in formatted value */
1088
+ if (newLeft) {
1089
+ position = newLeft[0].length;
1090
+ /** if we are just before sign which is in prefix position */
1091
+ if (((position === 0 && value.charAt(0) !== settingsClone.aNeg) || (position === 1 && value.charAt(0) === settingsClone.aNeg)) && settingsClone.aSign && settingsClone.pSign === 'p') {
1092
+ /** place caret after prefix sign */
1093
+ position = this.settingsClone.aSign.length + (value.charAt(0) === '-' ? 1 : 0);
1094
+ }
1095
+ } else {
1096
+ if (settingsClone.aSign && settingsClone.pSign === 's') {
1097
+ /** if we could not find a place for cursor and have a sign as a suffix */
1098
+ /** place caret before suffix currency sign */
1099
+ position -= settingsClone.aSign.length;
1100
+ }
1101
+ if (settingsClone.aSuffix) {
1102
+ /** if we could not find a place for cursor and have a suffix */
1103
+ /** place caret before suffix */
1104
+ position -= settingsClone.aSuffix.length;
1105
+ }
1106
+ }
1107
+ }
1108
+ this.that.value = value;
1109
+ this.setPosition(position);
1110
+ this.formatted = true;
1111
+ }
1112
+ };
1113
+
1114
+ /**
1115
+ * thanks to Anthony & Evan C
1116
+ */
1117
+ function autoGet(obj) {
1118
+ if (typeof obj === 'string') {
1119
+ obj = obj.replace(/\[/g, "\\[").replace(/\]/g, "\\]");
1120
+ obj = '#' + obj.replace(/(:|\.)/g, '\\$1');
1121
+ /** obj = '#' + obj.replace(/([;&,\.\+\*\~':"\!\^#$%@\[\]\(\)=>\|])/g, '\\$1'); */
1122
+ /** possible modification to replace the above 2 lines */
1123
+ }
1124
+ return $(obj);
1125
+ }
1126
+
1127
+ /**
1128
+ * function to attach data to the element
1129
+ * and imitate the holder
1130
+ */
1131
+ function getHolder($that, settings, update) {
1132
+ var data = $that.data('autoNumeric');
1133
+ if (!data) {
1134
+ data = {};
1135
+ $that.data('autoNumeric', data);
1136
+ }
1137
+ var holder = data.holder;
1138
+ if ((holder === undefined && settings) || update) {
1139
+ holder = new AutoNumericHolder($that.get(0), settings);
1140
+ data.holder = holder;
1141
+ }
1142
+ return holder;
1143
+ }
1144
+
1145
+ /**
1146
+ * original settings saved for use when eDec & nSep options are being used
1147
+ */
1148
+ function originalSettings(settings) {
1149
+ settings.oDec = settings.mDec;
1150
+ settings.oPad = settings.aPad;
1151
+ settings.oBracket = settings.nBracket;
1152
+ settings.oSep = settings.aSep;
1153
+ settings.oSign = settings.aSign;
1154
+ return settings;
1155
+ }
1156
+
1157
+ /**
1158
+ * original settings saved for use when eDec & nSep options are being used
1159
+ * taken from Quirksmode
1160
+ */
1161
+ function readCookie(name) {
1162
+ var nameEQ = name + "=",
1163
+ ca = document.cookie.split(';'),
1164
+ i = 0,
1165
+ c = '';
1166
+ for (i; i < ca.length; i += 1) {
1167
+ c = ca[i];
1168
+ while (c.charAt(0) === ' ') {
1169
+ c = c.substring(1, c.length);
1170
+ }
1171
+ if (c.indexOf(nameEQ) === 0) {
1172
+ return c.substring(nameEQ.length, c.length);
1173
+ }
1174
+ }
1175
+ return null;
1176
+ }
1177
+
1178
+ /**
1179
+ * Test if sessionStorage is supported - taken from moderizr
1180
+ */
1181
+ function storageTest() {
1182
+ var mod = 'modernizr';
1183
+ try {
1184
+ sessionStorage.setItem(mod, mod);
1185
+ sessionStorage.removeItem(mod);
1186
+ return true;
1187
+ } catch (e) {
1188
+ return false;
1189
+ }
1190
+ }
1191
+
1192
+ /**
1193
+ * creates or removes sessionStorage or cookie depending on browser support
1194
+ */
1195
+ function autoSave($this, settings, toDo) {
1196
+ if (settings.aStor) {
1197
+ var storedName = ($this[0].name !== '' && $this[0].name !== undefined) ? 'AUTO_' + decodeURIComponent($this[0].name) : 'AUTO_' + $this[0].id;
1198
+ if (storageTest() === false) { /** sets cookie for browser that do not support sessionStorage IE 6 & ie7 */
1199
+ if (toDo === 'get') {
1200
+ return readCookie(storedName);
1201
+ }
1202
+ if (toDo === 'set') {
1203
+ document.cookie = storedName + '=' + settings.rawValue + '; expires= ; path=/';
1204
+ }
1205
+ if (toDo === 'wipe') {
1206
+ var date = new Date();
1207
+ date.setTime(date.getTime() + (-1 * 24 * 60 * 60 * 1000));
1208
+ var expires = "; expires=" + date.toGMTString();
1209
+ document.cookie = storedName + '="" ;' + expires + '; path=/';
1210
+ }
1211
+ } else {
1212
+ if (toDo === 'get') {
1213
+ return sessionStorage.getItem(storedName);
1214
+ }
1215
+ if (toDo === 'set') {
1216
+ sessionStorage.setItem(storedName, settings.rawValue);
1217
+ }
1218
+ if (toDo === 'wipe') {
1219
+ sessionStorage.removeItem(storedName);
1220
+ }
1221
+ }
1222
+ }
1223
+ return;
1224
+ }
1225
+
1226
+ /**
1227
+ * Methods supported by autoNumeric
1228
+ */
1229
+ var methods = {
1230
+
1231
+ /**
1232
+ * Method to initiate autoNumeric and attached the settings (default and options passed as a parameter
1233
+ * $(someSelector).autoNumeric('init'); // initiate autoNumeric with defaults
1234
+ * $(someSelector).autoNumeric('init', {option}); // initiate autoNumeric with options
1235
+ * $(someSelector).autoNumeric(); // initiate autoNumeric with defaults
1236
+ * $(someSelector).autoNumeric({option}); // initiate autoNumeric with options
1237
+ * options passes as a parameter example '{aSep: '.', aDec: ',', aSign: '€ '}
1238
+ */
1239
+ init: function (options) {
1240
+ return this.each(function () {
1241
+ var $this = $(this),
1242
+ /** attempt to grab 'autoNumeric' settings, if they don't exist returns "undefined". */
1243
+ settings = $this.data('autoNumeric'),
1244
+ /** attempt to grab HTML5 data, if they don't exist we'll get "undefined".*/
1245
+ tagData = $this.data(),
1246
+ /** supported input types*/
1247
+ $input = $this.is('input[type=text], input[type=hidden], input[type=tel], input:not([type])');
1248
+ $.each(tagData, function (key, value) {
1249
+ if (typeof value === 'number') {
1250
+ tagData[key] = value.toString();
1251
+ }
1252
+ });
1253
+ if (typeof settings !== 'object') { /** If we couldn't grab settings, create them from defaults and passed options. */
1254
+ settings = $.extend({}, $.fn.autoNumeric.defaults, tagData, options, {
1255
+ aNum: '0123456789',
1256
+ onOff: false,
1257
+ runOnce: false,
1258
+ rawValue: '',
1259
+ trailingNegative: false,
1260
+ caretFix: false,
1261
+ throwInput: true,
1262
+ tagList: ['b', 'caption', 'cite', 'code', 'dd', 'del', 'div', 'dfn', 'dt', 'em', 'h1', 'h2', 'h3', 'h4', 'h5', 'h6', 'ins', 'kdb', 'label', 'li', 'option', 'output', 'p', 'q', 's', 'sample', 'span', 'strong', 'td', 'th', 'u', 'var']
1263
+ }); /** Merge defaults, tagData and options */
1264
+ if (settings.aDec === settings.aSep) {
1265
+ throwErr('autoNumeric will not function properly when the decimal character aDec: "' + settings.aDec + '" and thousand separator aSep: "' + settings.aSep + '" are the same character', settings.debug);
1266
+ }
1267
+ $.each(settings, function (key, value) {
1268
+ if (value === 'true' || value === 'false') {
1269
+ settings[key] = (value === 'true') ? true : false;
1270
+ }
1271
+ });
1272
+ $this.data('autoNumeric', settings); /** Save our new settings */
1273
+ } else {
1274
+ return this;
1275
+ }
1276
+ settings = originalSettings(settings); /** original settings saved for use when eDec & nSep options are being used */
1277
+ var holder = getHolder($this, settings);
1278
+ if (!$input && $this.prop('tagName').toLowerCase() === 'input') { /** checks for non-supported input types */
1279
+ throwErr('The input type "' + $this.prop('type') + '" is not supported by autoNumeric()', settings.debug);
1280
+ }
1281
+ if ($.inArray($this.prop('tagName').toLowerCase(), settings.tagList) === -1 && $this.prop('tagName').toLowerCase() !== 'input') { /** checks for non-supported tags */
1282
+ throwErr('The "<' + $this.prop('tagName').toLowerCase() + '>" is not supported by autoNumeric()', settings.debug);
1283
+ }
1284
+ if (settings.aDec === settings.aSep) { /** checks if the decimal and thousand are characters are the same */
1285
+ throwErr('autoNumeric will not function properly when the decimal character aDec: "' + settings.aDec + '" and thousand separator aSep: "' + settings.aSep + '" are the same character', settings.debug);
1286
+ }
1287
+ if (settings.eDec < settings.mDec && settings.eDec !== null) { /** checks the extended decimal places "eDec" is greater than the normal decimal places "mDec" */
1288
+ throwErr('autoNumeric will not function properly when the extended decimal places "eDec: ' + settings.eDec + '" is greater than mDec: "' + settings.mDec + '" value', settings.debug);
1289
+ }
1290
+ /** routine to format default value on page load */
1291
+ if (settings.runOnce === false && settings.aForm) {
1292
+ var setValue = true;
1293
+ if ($input) {
1294
+ /** checks for page reload from back button
1295
+ * also checks for ASP.net form post back
1296
+ * the following HTML data attribute is REQUIRED (data-an-default="same value as the value attribute")
1297
+ * example: <asp:TextBox runat="server" id="someID" text="1234.56" data-an-default="1234.56">
1298
+ */
1299
+ if ((settings.anDefault !== null && settings.anDefault.toString() !== $this.val()) || (settings.anDefault === null && $this.val() !== '' && $this.val() !== $this.attr('value')) || ($this.val() !== '' && $this.attr('type') === 'hidden' && !$.isNumeric($this.val().replace(',', '.')))) {
1300
+ if (settings.eDec !== null && settings.aStor) {
1301
+ settings.rawValue = autoSave($this, settings, 'get');
1302
+ }
1303
+ if (!settings.aStor) {
1304
+ var toStrip = '';
1305
+ if (settings.nBracket !== null && settings.aNeg !== '') {
1306
+ settings.onOff = true;
1307
+ toStrip = negativeBracket($this.val(), settings);
1308
+ } else {
1309
+ toStrip = $this.val();
1310
+ }
1311
+ settings.rawValue = ((settings.pNeg === 's' || (settings.pSign === 's' && settings.pNeg !== 'p')) && settings.aNeg !== '' && $this.val().indexOf('-') > -1) ? '-' + autoStrip(toStrip, settings) : autoStrip(toStrip, settings);
1312
+ }
1313
+ setValue = false;
1314
+ }
1315
+ if ($this.val() === '' && settings.wEmpty === 'focus') {
1316
+ setValue = false;
1317
+ }
1318
+ if ($this.val() === '' && settings.wEmpty === 'always') {
1319
+ $this.val(settings.aSign);
1320
+ setValue = false;
1321
+ }
1322
+ if (setValue && $this.val() !== '' && $this.val() === $this.attr('value')) {
1323
+ $this.autoNumeric('set', $this.val());
1324
+ }
1325
+ }
1326
+ if ($.inArray($this.prop('tagName').toLowerCase(), settings.tagList) !== -1 && $this.text() !== '') {
1327
+ if (settings.anDefault !== null) {
1328
+ if (settings.anDefault === $this.text()) {
1329
+ $this.autoNumeric('set', $this.text());
1330
+ }
1331
+ } else {
1332
+ $this.autoNumeric('set', $this.text());
1333
+ }
1334
+ }
1335
+ }
1336
+ settings.runOnce = true;
1337
+ if ($input) { /**input types supported "text", "hidden", "tel" and no type*/
1338
+ $this.on('focusin.autoNumeric', function () {
1339
+ holder = getHolder($this);
1340
+ var $settings = holder.settingsClone;
1341
+ $settings.onOff = true;
1342
+ if ($settings.nBracket !== null && $settings.aNeg !== '') {
1343
+ $this.val(negativeBracket($this.val(), $settings));
1344
+ }
1345
+ if ($settings.nSep === true) {
1346
+ $settings.aSep = '';
1347
+ $settings.aSign = '';
1348
+ }
1349
+ if ($settings.eDec !== null) {
1350
+ $settings.mDec = $settings.eDec;
1351
+ $this.autoNumeric('set', $settings.rawValue);
1352
+ } else {
1353
+ $this.autoNumeric('set', $settings.rawValue);
1354
+ }
1355
+ holder.inVal = $this.val();
1356
+ holder.lastVal = $this.val();
1357
+ var onEmpty = checkEmpty(holder.inVal, $settings, true);
1358
+ if ((onEmpty !== null && onEmpty !== '') && $settings.wEmpty === 'focus') {
1359
+ $this.val(onEmpty);
1360
+ }
1361
+ });
1362
+ $this.on('keydown.autoNumeric', function (e) {
1363
+ holder = getHolder($this);
1364
+ if (holder.that.readOnly) {
1365
+ holder.processed = true;
1366
+ return true;
1367
+ }
1368
+ /** The below streamed code / comment allows the "enter" keydown to throw a change() event */
1369
+ /** if (e.keyCode === 13 && holder.inVal !== $this.val()){
1370
+ $this.change();
1371
+ holder.inVal = $this.val();
1372
+ }*/
1373
+ holder.init(e);
1374
+ if (holder.skipAllways(e)) {
1375
+ holder.processed = true;
1376
+ return true;
1377
+ }
1378
+ if (holder.processAllways()) {
1379
+ holder.processed = true;
1380
+ holder.formatQuick(e);
1381
+ if (($this.val() !== holder.lastVal) && holder.settingsClone.throwInput) {
1382
+ $this.trigger('input'); /** throws input event in deletion character */
1383
+ }
1384
+ holder.lastVal = $this.val();
1385
+ holder.settingsClone.throwInput = true;
1386
+ e.preventDefault();
1387
+ return false;
1388
+ }
1389
+ holder.formatted = false;
1390
+ return true;
1391
+ });
1392
+ $this.on('keypress.autoNumeric', function (e) {
1393
+ if (e.shiftKey && e.keyCode === 45) { /** FF fix for Shift && insert paste event */
1394
+ return;
1395
+ }
1396
+ holder = getHolder($this);
1397
+ var processed = holder.processed;
1398
+ holder.init(e);
1399
+ if (holder.skipAllways(e)) {
1400
+ return true;
1401
+ }
1402
+ if (processed) {
1403
+ e.preventDefault();
1404
+ return false;
1405
+ }
1406
+ if (holder.processAllways() || holder.processKeypress()) {
1407
+ holder.formatQuick(e);
1408
+ if (($this.val() !== holder.lastVal) && holder.settingsClone.throwInput) {
1409
+ $this.trigger('input'); /** throws input event on adding character */
1410
+ }
1411
+ holder.lastVal = $this.val();
1412
+ holder.settingsClone.throwInput = true;
1413
+ e.preventDefault();
1414
+ return;
1415
+ }
1416
+ holder.formatted = false;
1417
+ });
1418
+ $this.on('keyup.autoNumeric', function (e) {
1419
+ holder = getHolder($this);
1420
+ holder.init(e);
1421
+ var skip = holder.skipAllways(e);
1422
+ holder.kdCode = 0;
1423
+ delete holder.valuePartsBeforePaste;
1424
+ if ($this[0].value === holder.settingsClone.aSign) { /** added to properly place the caret when only the currency sign is present */
1425
+ if (holder.settingsClone.pSign === 's') {
1426
+ setElementSelection(this, 0, 0);
1427
+ } else {
1428
+ setElementSelection(this, holder.settingsClone.aSign.length, holder.settingsClone.aSign.length);
1429
+ }
1430
+ }
1431
+ if ($this[0].value === holder.settingsClone.aSuffix) {
1432
+ setElementSelection(this, 0, 0);
1433
+ }
1434
+ if (holder.settingsClone.rawValue === '' && holder.settingsClone.aSign !== '' && holder.settingsClone.aSuffix !== '') {
1435
+ setElementSelection(this, 0, 0);
1436
+ }
1437
+ if (holder.settingsClone.eDec !== null && holder.settingsClone.aStor) { /** saves the extended decimal to preserve the data when navigating away from the page */
1438
+ autoSave($this, settings, 'set');
1439
+ }
1440
+ if (skip) {
1441
+ return true;
1442
+ }
1443
+ if (this.value === '') {
1444
+ return true;
1445
+ }
1446
+ if (!holder.formatted) {
1447
+ holder.formatQuick(e);
1448
+ }
1449
+ });
1450
+ $this.on('focusout.autoNumeric', function () {
1451
+ holder = getHolder($this);
1452
+ var value = $this.val(),
1453
+ origValue = value,
1454
+ $settings = holder.settingsClone;
1455
+ $settings.onOff = false;
1456
+ if ($settings.aStor) {
1457
+ autoSave($this, $settings, 'set');
1458
+ }
1459
+ if ($settings.nSep === true) {
1460
+ $settings.aSep = $settings.oSep;
1461
+ $settings.aSign = $settings.oSign;
1462
+ }
1463
+ if ($settings.eDec !== null) {
1464
+ $settings.mDec = $settings.oDec;
1465
+ $settings.aPad = $settings.oPad;
1466
+ $settings.nBracket = $settings.oBracket;
1467
+ }
1468
+ if (value !== '') {
1469
+ value = autoStrip(value, $settings);
1470
+ if ($settings.trailingNegative) {
1471
+ value = '-' + value;
1472
+ $settings.trailingNegative = false;
1473
+ }
1474
+ if (checkEmpty(value, $settings) === null && autoCheck(value, $settings, $this[0])) {
1475
+ value = fixNumber(value, $settings.aDec, $settings.aNeg);
1476
+ $settings.rawValue = value;
1477
+ value = autoRound(value, $settings);
1478
+ value = presentNumber(value, $settings.aDec, $settings.aNeg);
1479
+ } else {
1480
+ value = '';
1481
+ $settings.rawValue = '';
1482
+ }
1483
+ } else {
1484
+ $settings.rawValue = '';
1485
+ }
1486
+ var groupedValue = checkEmpty(value, $settings, false);
1487
+ if (groupedValue === null) {
1488
+ groupedValue = autoGroup(value, $settings);
1489
+ }
1490
+ if (groupedValue !== origValue) {
1491
+ $this.val(groupedValue);
1492
+ }
1493
+ if (groupedValue !== holder.inVal) {
1494
+ $this.change();
1495
+ delete holder.inVal;
1496
+ }
1497
+ });
1498
+ $this.on('paste.autoNumeric', function (e) {
1499
+ holder = getHolder($this);
1500
+ var clipboardData = e.clipboardData || e.originalEvent.clipboardData || window.clipboardData,
1501
+ pastedData = clipboardData.getData('text');
1502
+ if (pastedData !== holder.lastVal) {
1503
+ $this.trigger('input'); /** throws input event on adding character */
1504
+ holder.lastVal = window.setTimeout( function() {
1505
+ $this.val();
1506
+ }, 100);
1507
+ }
1508
+ });
1509
+ $this.closest('form').on('submit.autoNumeric', function () {
1510
+ holder = getHolder($this);
1511
+ var $settings = holder.settingsClone;
1512
+ if ($settings.unSetOnSubmit) {
1513
+ $this.val($settings.rawValue);
1514
+ }
1515
+
1516
+ });
1517
+ }
1518
+ });
1519
+ },
1520
+
1521
+ /**
1522
+ * method to remove settings and stop autoNumeric() - does not remove the formatting
1523
+ * $(someSelector).autoNumeric('destroy'); // destroys autoNumeric
1524
+ * no parameters accepted
1525
+ */
1526
+ destroy: function () {
1527
+ return $(this).each(function () {
1528
+ var $this = autoGet($(this)),
1529
+ settings = $this.data('autoNumeric');
1530
+ if (typeof settings === 'object') {
1531
+ $this.val('');
1532
+ autoSave($this, settings, 'wipe');
1533
+ $this.off('.autoNumeric');
1534
+ $this.removeData('autoNumeric');
1535
+ }
1536
+ });
1537
+ },
1538
+
1539
+ /**
1540
+ * method to clear the value and sessionStorage or cookie depending on browser supports
1541
+ * $(someSelector).autoNumeric('wipe'); // removes session storage and cookies from memory
1542
+ * no parameters accepted
1543
+ */
1544
+ wipe: function () {
1545
+ return $(this).each(function () {
1546
+ var $this = autoGet($(this)),
1547
+ settings = $this.data('autoNumeric');
1548
+ if (typeof settings === 'object') {
1549
+ $this.val('');
1550
+ settings.rawValue = '';
1551
+ autoSave($this, settings, 'wipe');
1552
+ }
1553
+ });
1554
+ },
1555
+
1556
+ /**
1557
+ * method to update settings - can be call as many times
1558
+ * $(someSelector).autoNumeric('update', {options}); // updates the settings
1559
+ * options passed as a parameter example '{aSep: '.', aDec: ',', aSign: '€ '}
1560
+ */
1561
+ update: function (options) {
1562
+ return $(this).each(function () {
1563
+ var $this = autoGet($(this)),
1564
+ settings = $this.data('autoNumeric');
1565
+ if (typeof settings !== 'object') {
1566
+ throwErr('Initializing autoNumeric is required prior to calling the "update" method', true);
1567
+ }
1568
+ var strip = $this.autoNumeric('get');
1569
+ settings = $.extend(settings, options);
1570
+ settings = originalSettings(settings);
1571
+ getHolder($this, settings, true);
1572
+ if (settings.aDec === settings.aSep) {
1573
+ throwErr('autoNumeric will not function properly when the decimal character aDec: "' + settings.aDec + '" and thousand separator aSep: "' + settings.aSep + '" are the same character', settings.debug);
1574
+ }
1575
+ $this.data('autoNumeric', settings);
1576
+ if ($this.val() !== '' || $this.text() !== '') {
1577
+ return $this.autoNumeric('set', strip);
1578
+ }
1579
+ return;
1580
+ });
1581
+ },
1582
+
1583
+ /**
1584
+ * method to format value sent as a parameter ""
1585
+ * $(someSelector).autoNumeric('set', 'value'}); // formats the value being passed
1586
+ * value passed as a string - can be a integer '1234' or double '1234.56789'
1587
+ * must contain only numbers and one decimal (period) character
1588
+ */
1589
+ set: function (valueIn) {
1590
+ return $(this).each(function () {
1591
+ if (valueIn === null) {
1592
+ return;
1593
+ }
1594
+ var $this = autoGet($(this)),
1595
+ settings = $this.data('autoNumeric'),
1596
+ value = valueIn.toString(),
1597
+ $input = $this.is('input[type=text], input[type=hidden], input[type=tel], input:not([type])');
1598
+ if (typeof settings !== 'object') {
1599
+ throwErr('Initializing autoNumeric is required prior to calling the "set" method', true);
1600
+ }
1601
+ /** allows locale decimal separator to be a comma - no thousand separator allowed */
1602
+ value = convertLocale(value);
1603
+ /** Throws an error if the value being set is not numeric */
1604
+ if (!$.isNumeric(Number(value))) {
1605
+ throwErr('The value "' + value + '" being "set" is not numeric and has caused a error to be thrown', settings.debug);
1606
+ }
1607
+ if (value !== '') {
1608
+ if (autoCheck(value, settings)) {
1609
+ if ($input && settings.eDec !== null) {
1610
+ settings.rawValue = value;
1611
+ }
1612
+ if ($input || $.inArray($this.prop('tagName').toLowerCase(), settings.tagList) !== -1) { /** checks if the value falls within the min max range */
1613
+ value = autoRound(value, settings);
1614
+ if (settings.eDec === null) {
1615
+ settings.rawValue = value;
1616
+ }
1617
+ value = presentNumber(value, settings.aDec, settings.aNeg);
1618
+ value = autoGroup(value, settings);
1619
+ }
1620
+ if (settings.aStor && settings.eDec !== null) {
1621
+ autoSave($this, settings, 'set');
1622
+ }
1623
+ } else {
1624
+ settings.rawValue = '';
1625
+ autoSave($this, settings, 'wipe');
1626
+ value = '';
1627
+ throwErr('The value being set falls outside the min: "' + settings.vMin + ' max: "' + settings.vMax + '" ) settings for this element', settings.debug);
1628
+ return '';
1629
+ }
1630
+ } else {
1631
+ return '';
1632
+ }
1633
+ if ($input) {
1634
+ return $this.val(value);
1635
+ }
1636
+ if ($.inArray($this.prop('tagName').toLowerCase(), settings.tagList) !== -1) {
1637
+ return $this.text(value);
1638
+ }
1639
+ return false;
1640
+ });
1641
+ },
1642
+
1643
+ /**
1644
+ * method to un-format inputs - handy to use right before form submission
1645
+ * $(someSelector).autoNumeric('unSet'); // parameter optional
1646
+ * $(someSelector).autoNumeric('unSet', 'komma'); // returns string '1234,56' with a komma as the decimal character
1647
+ * $(someSelector).autoNumeric('unSet', 'checkOptions'); // returns string '1234.56' or '1234.56' depending of the format setting for the input
1648
+ */
1649
+ unSet: function (outPut) {
1650
+ return $(this).each(function () {
1651
+ var $this = autoGet($(this)),
1652
+ settings = $this.data('autoNumeric');
1653
+ if (typeof settings === 'object') {
1654
+ settings.onOff = true;
1655
+ $this.val($this.autoNumeric('get', outPut));
1656
+ }
1657
+ });
1658
+ },
1659
+
1660
+ /**
1661
+ * method to re-format inputs - handy to use right after form submission
1662
+ * $(someSelector).autoNumeric('reSet'); // no parameters accepted
1663
+ * this is called after the 'unSet' method to reformat the input
1664
+ */
1665
+ reSet: function () {
1666
+ return $(this).each(function () {
1667
+ var $this = autoGet($(this)),
1668
+ settings = $this.data('autoNumeric');
1669
+ if (typeof settings === 'object') {
1670
+ $this.autoNumeric('set', $this.val());
1671
+ }
1672
+ });
1673
+ },
1674
+
1675
+ /**
1676
+ * method to get the unformatted that accepts up to one parameter
1677
+ * $(someSelector).autoNumeric('get'); no parameter used - values returned as ISO numeric string "1234.56" where the decimal character is a period
1678
+ * $(someSelector).autoNumeric('get', 'asKomma'); values returned as strings "nnnn,nn" where the comma / komma is the decimal character
1679
+ * $(someSelector).autoNumeric('get', 'checkOptions'); values returned as strings - either as "nnnn.nn" or "nnnn,mm" depending of the format setting for the input
1680
+ * only the first element in the selector is returned
1681
+ */
1682
+ get: function (outPut) {
1683
+ var $this = autoGet($(this)),
1684
+ settings = $this.data('autoNumeric'),
1685
+ $input = $this.is('input[type=text], input[type=hidden], input[type=tel], input:not([type])');
1686
+ if (typeof settings !== 'object') {
1687
+ throwErr('Initializing autoNumeric is required prior to calling the "get" method', true);
1688
+ }
1689
+ var getValue = '';
1690
+ /** determine the element type then use .eq(0) selector to grab the value of the first element in selector */
1691
+ if ($input) {
1692
+ getValue = $this.eq(0).val();
1693
+ } else if ($.inArray($this.prop('tagName').toLowerCase(), settings.tagList) !== -1) {
1694
+ getValue = $this.eq(0).text();
1695
+ } else {
1696
+ throwErr('The "<' + $this.prop('tagName').toLowerCase() + '>" is not supported by autoNumeric()', settings.debug);
1697
+ }
1698
+ if (settings.rawValue !== '') {
1699
+ getValue = settings.rawValue;
1700
+ }
1701
+ if (((!/\d/).test(getValue) || Number(getValue) === 0) && settings.wEmpty === 'focus') {
1702
+ return '';
1703
+ }
1704
+ if (getValue !== '' && settings.nBracket !== null) {
1705
+ settings.onOff = true;
1706
+ getValue = negativeBracket(getValue, settings);
1707
+ }
1708
+ getValue = fixNumber(getValue, settings.aDec, settings.aNeg);
1709
+ if (Number(getValue) === 0 && settings.lZero !== 'keep') {
1710
+ getValue = '0';
1711
+ }
1712
+ if (outPut === ',') {
1713
+ getValue = getValue.replace('.', ',');
1714
+ }
1715
+ if (outPut === '.-' && getValue.indexOf('-') > -1) {
1716
+ getValue = getValue.replace('-', '') + '-';
1717
+ }
1718
+ if (outPut === ',-' && getValue.indexOf('-') > -1) {
1719
+ getValue = getValue.replace('.', ',').replace('-', '') + '-';
1720
+ }
1721
+ return getValue; /** returned Numeric String */
1722
+ },
1723
+
1724
+ /**
1725
+ * The 'getString' method used jQuerys .serialize() method that creates a text string in standard URL-encoded notation
1726
+ * it then loops through the string and un-formats the inputs with autoNumeric
1727
+ * $(someSelector).autoNumeric('getString'); no parameter used - values returned as ISO numeric string "1234.56" where the decimal character is a period
1728
+ * $(someSelector).autoNumeric('getString', 'asKomma'); values returned as strings "nnnn,nn" where the comma / komma is the decimal character
1729
+ * $(someSelector).autoNumeric('getString', 'checkOptions'); values returned as strings - either as "nnnn.nn" or "nnnn,mm" depending of the format setting for the input
1730
+ */
1731
+ getString: function (outPut) {
1732
+ var $this = autoGet($(this)),
1733
+ formFields = $this.serialize(),
1734
+ formParts = formFields.split('&'),
1735
+ formIndex = $('form').index($this),
1736
+ allFormElements = $('form:eq(' + formIndex + ')'),
1737
+ aiIndex = [], /** all input index */
1738
+ scIndex = [], /** successful control index */
1739
+ rsubmitterTypes = /^(?:submit|button|image|reset|file)$/i, /* from jQuery serialize method */
1740
+ rsubmittable = /^(?:input|select|textarea|keygen)/i, /* from jQuery serialize method */
1741
+ rcheckableType = /^(?:checkbox|radio)$/i,
1742
+ rnonAutoNumericTypes = /^(?:button|checkbox|color|date|datetime|datetime-local|email|file|image|month|number|password|radio|range|reset|search|submit|time|url|week)/i,
1743
+ count = 0;
1744
+ /*jslint unparam: true*/
1745
+ /** index of successful elements */
1746
+ $.each(allFormElements[0], function (i, field) {
1747
+ if (field.name !== '' && rsubmittable.test(field.localName) && !rsubmitterTypes.test(field.type) && !field.disabled && (field.checked || !rcheckableType.test(field.type))) {
1748
+ scIndex.push(count);
1749
+ count = count + 1;
1750
+ } else {
1751
+ scIndex.push(-1);
1752
+ }
1753
+ });
1754
+ /** index of all inputs tags except checkbox */
1755
+ count = 0;
1756
+ $.each(allFormElements[0], function (i, field) {
1757
+ if (field.localName === 'input' && (field.type === '' || field.type === 'text' || field.type === 'hidden' || field.type === 'tel')) {
1758
+ aiIndex.push(count);
1759
+ count = count + 1;
1760
+ } else {
1761
+ aiIndex.push(-1);
1762
+ if (field.localName === 'input' && rnonAutoNumericTypes.test(field.type)) {
1763
+ count = count + 1;
1764
+ }
1765
+ }
1766
+ });
1767
+ $.each(formParts, function (i, miniParts) {
1768
+ miniParts = formParts[i].split('=');
1769
+ var scElement = $.inArray(i, scIndex);
1770
+ if (scElement > -1 && aiIndex[scElement] > -1) {
1771
+ var testInput = $('form:eq(' + formIndex + ') input:eq(' + aiIndex[scElement] + ')'),
1772
+ settings = testInput.data('autoNumeric');
1773
+ if (typeof settings === 'object') {
1774
+ if (miniParts[1] !== null) {
1775
+ miniParts[1] = $('form:eq(' + formIndex + ') input:eq(' + aiIndex[scElement] + ')').autoNumeric('get', outPut).toString();
1776
+ formParts[i] = miniParts.join('=');
1777
+ }
1778
+ }
1779
+ }
1780
+ });
1781
+ /*jslint unparam: false*/
1782
+ return formParts.join('&');
1783
+ },
1784
+
1785
+ /**
1786
+ * The 'getString' method used jQuerys .serializeArray() method that creates array or objects that can be encoded as a JSON string
1787
+ * it then loops through the string and un-formats the inputs with autoNumeric
1788
+ * $(someSelector).autoNumeric('getArray'); no parameter used - values returned as ISO numeric string "1234.56" where the decimal character is a period
1789
+ * $(someSelector).autoNumeric('getArray', 'asKomma'); values returned as strings "nnnn,nn" where the comma / komma is the decimal character
1790
+ * $(someSelector).autoNumeric('getArray', 'checkOptions'); values returned as strings - either as "nnnn.nn" or "nnnn,mm" depending of the format setting for the input
1791
+ */
1792
+ getArray: function (outPut) {
1793
+ var $this = autoGet($(this)),
1794
+ formFields = $this.serializeArray(),
1795
+ formIndex = $('form').index($this),
1796
+ allFormElements = $('form:eq(' + formIndex + ')'),
1797
+ aiIndex = [], /* all input index */
1798
+ scIndex = [], /* successful control index */
1799
+ rsubmitterTypes = /^(?:submit|button|image|reset|file)$/i, /* from jQuery serialize method */
1800
+ rsubmittable = /^(?:input|select|textarea|keygen)/i, /* from jQuery serialize method */
1801
+ rcheckableType = /^(?:checkbox|radio)$/i,
1802
+ rnonAutoNumericTypes = /^(?:button|checkbox|color|date|datetime|datetime-local|email|file|image|month|number|password|radio|range|reset|search|submit|time|url|week)/i,
1803
+ count = 0;
1804
+ /*jslint unparam: true*/
1805
+ /* index of successful elements */
1806
+ $.each(allFormElements[0], function (i, field) {
1807
+ if (field.name !== '' && rsubmittable.test(field.localName) && !rsubmitterTypes.test(field.type) && !field.disabled && (field.checked || !rcheckableType.test(field.type))) {
1808
+ scIndex.push(count);
1809
+ count = count + 1;
1810
+ } else {
1811
+ scIndex.push(-1);
1812
+ }
1813
+ });
1814
+ /* index of all inputs tags */
1815
+ count = 0;
1816
+ $.each(allFormElements[0], function (i, field) {
1817
+ if (field.localName === 'input' && (field.type === '' || field.type === 'text' || field.type === 'hidden' || field.type === 'tel')) {
1818
+ aiIndex.push(count);
1819
+ count = count + 1;
1820
+ } else {
1821
+ aiIndex.push(-1);
1822
+ if (field.localName === 'input' && rnonAutoNumericTypes.test(field.type)) {
1823
+ count = count + 1;
1824
+ }
1825
+ }
1826
+ });
1827
+ $.each(formFields, function (i, field) {
1828
+ var scElement = $.inArray(i, scIndex);
1829
+ if (scElement > -1 && aiIndex[scElement] > -1) {
1830
+ var testInput = $('form:eq(' + formIndex + ') input:eq(' + aiIndex[scElement] + ')'),
1831
+ settings = testInput.data('autoNumeric');
1832
+ if (typeof settings === 'object') {
1833
+ field.value = $('form:eq(' + formIndex + ') input:eq(' + aiIndex[scElement] + ')').autoNumeric('get', outPut).toString();
1834
+ }
1835
+ }
1836
+ });
1837
+ /*jslint unparam: false*/
1838
+ return formFields;
1839
+ },
1840
+
1841
+ /**
1842
+ * The 'getSteetings returns the object with autoNumeric settings for those who need to look under the hood
1843
+ * $(someSelector).autoNumeric('getSettings'); // no parameters accepted
1844
+ * $(someSelector).autoNumeric('getSettings').aDec; // return the aDec setting as a string - ant valid setting can be used
1845
+ */
1846
+ getSettings: function () {
1847
+ var $this = autoGet($(this));
1848
+ return $this.eq(0).data('autoNumeric');
1849
+ }
1850
+ };
1851
+
1852
+ /**
1853
+ * autoNumeric function
1854
+ */
1855
+ $.fn.autoNumeric = function (method) {
1856
+ if (methods[method]) {
1857
+ return methods[method].apply(this, Array.prototype.slice.call(arguments, 1));
1858
+ }
1859
+ if (typeof method === 'object' || !method) {
1860
+ return methods.init.apply(this, arguments);
1861
+ }
1862
+ throwErr('Method "' + method + '" is not supported by autoNumeric()', true);
1863
+ };
1864
+
1865
+ /**
1866
+ * Defaults are public - these can be overridden by the following:
1867
+ * HTML5 data attributes
1868
+ * Options passed by the 'init' or 'update' methods
1869
+ * Use jQuery's $.extend method for global changes - also a great way to pass ASP.NET current culture settings
1870
+ */
1871
+ $.fn.autoNumeric.defaults = {
1872
+ /** allowed thousand separator characters
1873
+ * comma = ','
1874
+ * period "full stop" = '.'
1875
+ * apostrophe is escaped = '\''
1876
+ * space = ' '
1877
+ * none = ''
1878
+ * NOTE: do not use numeric characters
1879
+ */
1880
+ aSep: ',',
1881
+ /** when true => when the input has focus only the decimal character is visible
1882
+ */
1883
+ nSep: false,
1884
+ /** digital grouping for the thousand separator used in Format
1885
+ * dGroup: '2', results in 99,99,99,999 India's lakhs
1886
+ * dGroup: '2s', results in 99,999,99,99,999 India's lakhs scaled
1887
+ * dGroup: '3', results in 999,999,999 default
1888
+ * dGroup: '4', results in 9999,9999,9999 used in some Asian countries
1889
+ */
1890
+ dGroup: '3',
1891
+ /** allowed decimal separator characters
1892
+ * period "full stop" = '.'
1893
+ * comma = ','
1894
+ */
1895
+ aDec: '.',
1896
+ /** allow to declare alternative decimal separator which is automatically replaced by aDec
1897
+ * developed for countries the use a comma ',' as the decimal character
1898
+ * and have keyboards\numeric pads that have a period 'full stop' as the decimal characters (Spain is an example)
1899
+ */
1900
+ altDec: null,
1901
+ /** aSign = allowed currency symbol
1902
+ * Must be in quotes aSign: '$'
1903
+ * space to the right of the currency symbol aSign: '$ '
1904
+ * space to the left of the currency symbol aSign: ' $'
1905
+ */
1906
+ aSign: '',
1907
+ /** pSign = placement of currency sign as a p=prefix or s=suffix
1908
+ * for prefix pSign: 'p' (default)
1909
+ * for suffix pSign: 's'
1910
+ */
1911
+ pSign: 'p',
1912
+ /** placement of negative sign relative to the aSign option l=left, r=right, p=prefix & s=suffix
1913
+ * -1,234.56 => defaults no options required
1914
+ * 1,234.56- => {pNeg: 's'}
1915
+ * -$1,234.56 => {aSign: '$'}
1916
+ * $-1,234.56 => {aSign: '$', pNeg: 'r'}
1917
+ * $1,234.56- => {aSign: '$', pNeg: 's'}
1918
+ * 1,234.56-$ => {aSign: '$', pSign: 's'}
1919
+ * 1,234.56$- => {aSign: '$', pSign: 's', pNeg: 'r'}
1920
+ * -1,234.56$ => {aSign: '$', pSign: 's', pNeg: 'p'}
1921
+ */
1922
+ pNeg: 'l',
1923
+ /** Additional suffix
1924
+ * Must be in quotes aSuffix: 'gross', a space is allowed aSuffix: ' dollars'
1925
+ * Numeric characters and negative sign not allowed'
1926
+ */
1927
+ aSuffix: '',
1928
+ /** maximum possible value
1929
+ * value must be enclosed in quotes and use the period for the decimal point
1930
+ * value must be larger than vMin
1931
+ */
1932
+ vMax: '9999999999999.99',
1933
+ /** minimum possible value
1934
+ * value must be enclosed in quotes and use the period for the decimal point
1935
+ * value must be smaller than vMax
1936
+ */
1937
+ vMin: '-9999999999999.99',
1938
+ /** Maximum number of decimal places = used to override decimal places set by the vMin & vMax values
1939
+ * value must be enclosed in quotes example mDec: '3',
1940
+ */
1941
+ mDec: null,
1942
+ /** Expanded decimal places visible when input has focus
1943
+ * value must be enclosed in quotes example mDec: '3',
1944
+ */
1945
+ eDec: null,
1946
+ /** Set to true to allow the eDec value to be saved with sessionStorage
1947
+ * if ie 6 or 7 the value will be saved as a session cookie
1948
+ */
1949
+ aStor: false,
1950
+ /** method used for rounding
1951
+ * mRound: 'S', Round-Half-Up Symmetric (default)
1952
+ * mRound: 'A', Round-Half-Up Asymmetric
1953
+ * mRound: 's', Round-Half-Down Symmetric (lower case s)
1954
+ * mRound: 'a', Round-Half-Down Asymmetric (lower case a)
1955
+ * mRound: 'B', Round-Half-Even "Bankers Rounding"
1956
+ * mRound: 'U', Round Up "Round-Away-From-Zero"
1957
+ * mRound: 'D', Round Down "Round-Toward-Zero" - same as truncate
1958
+ * mRound: 'C', Round to Ceiling "Toward Positive Infinity"
1959
+ * mRound: 'F', Round to Floor "Toward Negative Infinity"
1960
+ * mRound: 'N05' Rounds to the nearest .05
1961
+ * mRound: 'U05' Rounds up to next .05
1962
+ * mRound: 'D05' Rounds down to next .05
1963
+ */
1964
+ mRound: 'S',
1965
+ /** controls decimal padding
1966
+ * aPad: true - always Pad decimals with zeros
1967
+ * aPad: false - does not pad with zeros.
1968
+ * aPad: `some number` - pad decimals with zero to number different from mDec
1969
+ * thanks to Jonas Johansson for the suggestion
1970
+ */
1971
+ aPad: true,
1972
+ /** places brackets on negative value -$ 999.99 to (999.99)
1973
+ * visible only when the field does NOT have focus the left and right symbols should be enclosed in quotes and separated by a comma
1974
+ * nBracket: null - (default)
1975
+ * nBracket: '(,)', nBracket: '[,]', nBracket: '<,>' or nBracket: '{,}'
1976
+ */
1977
+ nBracket: null,
1978
+ /** Displayed on empty string ""
1979
+ * wEmpty: 'focus' - (default) currency sign displayed and the input receives focus
1980
+ * wEmpty: 'press' - currency sign displays on any key being pressed
1981
+ * wEmpty: 'always' - always displays the currency sign
1982
+ */
1983
+ wEmpty: 'focus',
1984
+ /** controls leading zero behavior
1985
+ * lZero: 'allow', - allows leading zeros to be entered. Zeros will be truncated when entering additional digits. On focusout zeros will be deleted.
1986
+ * lZero: 'deny', - allows only one leading zero on values less than one
1987
+ * lZero: 'keep', - allows leading zeros to be entered. on focusout zeros will be retained.
1988
+ */
1989
+ lZero: 'allow',
1990
+ /** determine if the default value will be formatted on page ready.
1991
+ * true = automatically formats the default value on page ready
1992
+ * false = will not format the default value
1993
+ */
1994
+ aForm: true,
1995
+ /** determine if the select all keyboard command will select
1996
+ * the complete input text or only the input numeric value
1997
+ * if the currency symbol is between the numeric value and the negative sign only the numeric value will selected
1998
+ */
1999
+ sNumber: false,
2000
+ /** helper option for ASP.NET postback
2001
+ * should be the value of the unformatted default value
2002
+ * examples:
2003
+ * no default value='' {anDefault: ''}
2004
+ * value=1234.56 {anDefault: '1234.56'}
2005
+ */
2006
+ anDefault: null,
2007
+ /** removes formatting on submit event
2008
+ * this output format: positive nnnn.nn, negative -nnnn.nn
2009
+ * review the 'unSet' method for other formats
2010
+ */
2011
+ unSetOnSubmit: false,
2012
+ /** error handling function
2013
+ * true => all errors are thrown - helpful in site development
2014
+ * false => throws errors when calling methods prior to the supported element has been initialized be autoNumeric
2015
+ */
2016
+ debug: true
2017
+ };
2018
+ }));