|
9 | 9 | v-model="amount"
|
10 | 10 | v-if="!readOnly"
|
11 | 11 | >
|
12 |
| - <span v-else ref="readOnly">{{ amount }}</span> |
| 12 | + <span |
| 13 | + v-else |
| 14 | + ref="readOnly" |
| 15 | + >{{ amount }}</span> |
13 | 16 | </template>
|
14 | 17 |
|
15 | 18 | <script>
|
16 | 19 | import accounting from 'accounting-js'
|
17 | 20 |
|
18 | 21 | export default {
|
19 |
| - name: 'vue-numeric', |
| 22 | + name: 'VueNumeric', |
20 | 23 |
|
21 | 24 | props: {
|
22 | 25 | /**
|
23 | 26 | * Currency symbol.
|
24 | 27 | */
|
25 | 28 | currency: {
|
| 29 | + type: String, |
26 | 30 | default: '',
|
27 |
| - required: false, |
28 |
| - type: String |
| 31 | + required: false |
29 | 32 | },
|
30 | 33 |
|
31 | 34 | /**
|
32 | 35 | * Maximum value allowed.
|
33 | 36 | */
|
34 | 37 | max: {
|
| 38 | + type: Number, |
35 | 39 | default: Number.MAX_SAFE_INTEGER || 9007199254740991,
|
36 | 40 | required: false,
|
37 |
| - type: Number |
38 | 41 | },
|
39 | 42 |
|
40 | 43 | /**
|
41 | 44 | * Minimum value allowed.
|
42 | 45 | */
|
43 | 46 | min: {
|
| 47 | + type: Number, |
44 | 48 | default: Number.MIN_SAFE_INTEGER || -9007199254740991,
|
45 |
| - required: false, |
46 |
| - type: Number |
| 49 | + required: false |
47 | 50 | },
|
48 | 51 |
|
49 | 52 | /**
|
50 | 53 | * Enable/Disable minus value.
|
51 | 54 | */
|
52 | 55 | minus: {
|
| 56 | + type: Boolean, |
53 | 57 | default: false,
|
54 |
| - required: false, |
55 |
| - type: Boolean |
| 58 | + required: false |
56 | 59 | },
|
57 | 60 |
|
58 | 61 | /**
|
59 | 62 | * Input placeholder.
|
60 | 63 | */
|
61 | 64 | placeholder: {
|
62 |
| - required: false, |
63 |
| - type: String |
| 65 | + type: String, |
| 66 | + default: '', |
| 67 | + required: false |
64 | 68 | },
|
65 | 69 |
|
66 | 70 | /**
|
67 | 71 | * Value when the input is empty
|
68 | 72 | */
|
69 | 73 | emptyValue: {
|
| 74 | + type: [Number, String], |
70 | 75 | default: '',
|
71 |
| - required: false, |
72 |
| - type: [Number, String] |
| 76 | + required: false |
73 | 77 | },
|
74 | 78 |
|
75 | 79 | /**
|
76 | 80 | * Number of decimals.
|
77 | 81 | * Decimals symbol are the opposite of separator symbol.
|
78 | 82 | */
|
79 | 83 | precision: {
|
80 |
| - required: false, |
81 |
| - type: Number |
| 84 | + type: Number, |
| 85 | + default: 0, |
| 86 | + required: false |
82 | 87 | },
|
83 | 88 |
|
84 | 89 | /**
|
85 | 90 | * Thousand separator type.
|
86 | 91 | * Separator props accept either . or , (default).
|
87 | 92 | */
|
88 | 93 | separator: {
|
| 94 | + type: String, |
89 | 95 | default: ',',
|
90 |
| - required: false, |
91 |
| - type: String |
| 96 | + required: false |
92 | 97 | },
|
93 | 98 |
|
94 | 99 | /**
|
95 | 100 | * v-model value.
|
96 | 101 | */
|
97 | 102 | value: {
|
| 103 | + type: [Number, String], |
98 | 104 | default: 0,
|
99 |
| - required: true, |
100 |
| - type: [Number, String] |
| 105 | + required: true |
101 | 106 | },
|
102 | 107 |
|
103 | 108 | /**
|
104 | 109 | * Hide input and show value in text only.
|
105 | 110 | */
|
106 | 111 | readOnly: {
|
| 112 | + type: Boolean, |
107 | 113 | default: false,
|
108 |
| - required: false, |
109 |
| - type: Boolean |
| 114 | + required: false |
110 | 115 | },
|
111 | 116 |
|
112 | 117 | /**
|
113 | 118 | * Class for the span tag when readOnly props is true.
|
114 | 119 | */
|
115 | 120 | readOnlyClass: {
|
| 121 | + type: String, |
116 | 122 | default: '',
|
117 |
| - required: false, |
118 |
| - type: String |
| 123 | + required: false |
119 | 124 | },
|
120 | 125 |
|
121 | 126 | /**
|
122 | 127 | * Position of currency symbol
|
123 | 128 | * Symbol position props accept either 'suffix' or 'prefix' (default).
|
124 | 129 | */
|
125 | 130 | currencySymbolPosition: {
|
| 131 | + type: String, |
126 | 132 | default: 'prefix',
|
127 |
| - required: false, |
128 |
| - type: String |
| 133 | + required: false |
129 | 134 | }
|
130 | 135 | },
|
131 | 136 |
|
@@ -179,6 +184,72 @@ export default {
|
179 | 184 | }
|
180 | 185 | },
|
181 | 186 |
|
| 187 | + watch: { |
| 188 | + /** |
| 189 | + * Watch for value change from other input with same v-model. |
| 190 | + * @param {Number} newValue |
| 191 | + */ |
| 192 | + valueNumber (newValue) { |
| 193 | + if (this.$refs.numeric !== document.activeElement) { |
| 194 | + this.amount = this.format(newValue) |
| 195 | + } |
| 196 | + }, |
| 197 | +
|
| 198 | + /** |
| 199 | + * When readOnly is true, replace the span tag class. |
| 200 | + * @param {Boolean} newValue |
| 201 | + * @param {Boolean} oldValue |
| 202 | + */ |
| 203 | + readOnly (newValue, oldValue) { |
| 204 | + if (oldValue === false && newValue === true) { |
| 205 | + this.$nextTick(() => { |
| 206 | + this.$refs.readOnly.className = this.readOnlyClass |
| 207 | + }) |
| 208 | + } |
| 209 | + }, |
| 210 | +
|
| 211 | + /** |
| 212 | + * Immediately reflect separator changes |
| 213 | + */ |
| 214 | + separator () { |
| 215 | + this.process(this.valueNumber) |
| 216 | + this.amount = this.format(this.valueNumber) |
| 217 | + }, |
| 218 | +
|
| 219 | + /** |
| 220 | + * Immediately reflect currency changes |
| 221 | + */ |
| 222 | + currency () { |
| 223 | + this.process(this.valueNumber) |
| 224 | + this.amount = this.format(this.valueNumber) |
| 225 | + }, |
| 226 | +
|
| 227 | + /** |
| 228 | + * Immediately reflect precision changes |
| 229 | + */ |
| 230 | + precision () { |
| 231 | + this.process(this.valueNumber) |
| 232 | + this.amount = this.format(this.valueNumber) |
| 233 | + } |
| 234 | + }, |
| 235 | +
|
| 236 | + mounted () { |
| 237 | + // Set default value props when placeholder undefined. |
| 238 | + if (!this.placeholder) { |
| 239 | + this.process(this.valueNumber) |
| 240 | + this.amount = this.format(this.valueNumber) |
| 241 | +
|
| 242 | + // In case of delayed props value. |
| 243 | + setTimeout(() => { |
| 244 | + this.process(this.valueNumber) |
| 245 | + this.amount = this.format(this.valueNumber) |
| 246 | + }, 500) |
| 247 | + } |
| 248 | +
|
| 249 | + // Set read-only span element's class |
| 250 | + if (this.readOnly) this.$refs.readOnly.className = this.readOnlyClass |
| 251 | + }, |
| 252 | +
|
182 | 253 | methods: {
|
183 | 254 | /**
|
184 | 255 | * Handle blur event.
|
@@ -258,72 +329,6 @@ export default {
|
258 | 329 | const toUnformat = typeof value === 'string' && value === '' ? this.emptyValue : value
|
259 | 330 | return accounting.unformat(toUnformat, this.decimalSeparator)
|
260 | 331 | }
|
261 |
| - }, |
262 |
| -
|
263 |
| - watch: { |
264 |
| - /** |
265 |
| - * Watch for value change from other input with same v-model. |
266 |
| - * @param {Number} newValue |
267 |
| - */ |
268 |
| - valueNumber (newValue) { |
269 |
| - if (this.$refs.numeric !== document.activeElement) { |
270 |
| - this.amount = this.format(newValue) |
271 |
| - } |
272 |
| - }, |
273 |
| -
|
274 |
| - /** |
275 |
| - * When readOnly is true, replace the span tag class. |
276 |
| - * @param {Boolean} newValue |
277 |
| - * @param {Boolean} oldValue |
278 |
| - */ |
279 |
| - readOnly (newValue, oldValue) { |
280 |
| - if (oldValue === false && newValue === true) { |
281 |
| - this.$nextTick(() => { |
282 |
| - this.$refs.readOnly.className = this.readOnlyClass |
283 |
| - }) |
284 |
| - } |
285 |
| - }, |
286 |
| -
|
287 |
| - /** |
288 |
| - * Immediately reflect separator changes |
289 |
| - */ |
290 |
| - separator () { |
291 |
| - this.process(this.valueNumber) |
292 |
| - this.amount = this.format(this.valueNumber) |
293 |
| - }, |
294 |
| -
|
295 |
| - /** |
296 |
| - * Immediately reflect currency changes |
297 |
| - */ |
298 |
| - currency () { |
299 |
| - this.process(this.valueNumber) |
300 |
| - this.amount = this.format(this.valueNumber) |
301 |
| - }, |
302 |
| -
|
303 |
| - /** |
304 |
| - * Immediately reflect precision changes |
305 |
| - */ |
306 |
| - precision () { |
307 |
| - this.process(this.valueNumber) |
308 |
| - this.amount = this.format(this.valueNumber) |
309 |
| - } |
310 |
| - }, |
311 |
| -
|
312 |
| - mounted () { |
313 |
| - // Set default value props when placeholder undefined. |
314 |
| - if (!this.placeholder) { |
315 |
| - this.process(this.valueNumber) |
316 |
| - this.amount = this.format(this.valueNumber) |
317 |
| -
|
318 |
| - // In case of delayed props value. |
319 |
| - setTimeout(() => { |
320 |
| - this.process(this.valueNumber) |
321 |
| - this.amount = this.format(this.valueNumber) |
322 |
| - }, 500) |
323 |
| - } |
324 |
| -
|
325 |
| - // Set read-only span element's class |
326 |
| - if (this.readOnly) this.$refs.readOnly.className = this.readOnlyClass |
327 | 332 | }
|
328 | 333 | }
|
329 | 334 | </script>
|
0 commit comments