Blame view

components/input-number/input-number.vue 6.81 KB
7fa943eb   梁灏   init
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
  <template>
      <div :class="wrapClasses">
          <div :class="handlerClasses">
              <a
                  @click="up"
                  @mouse.down="preventDefault"
                  :class="upClasses">
                  <span
                      :class="innerUpClasses"
                      @click="preventDefault">+</span>
              </a>
              <a
                  @click="down"
                  @mouse.down="preventDefault"
                  :class="downClasses">
                  <span
                      :class="innerDownClasses"
                      @click="preventDefault">-</span>
              </a>
          </div>
          <div :class="inputWrapClasses">
              <input
                  :class="inputClasses"
                  :disabled="disabled"
                  autoComplete="off"
                  @focus="focus"
                  @blur="blur"
                  @keydown.stop="keyDown"
                  @change="change"
                  :value="value">
          </div>
      </div>
  </template>
  <script>
      import { oneOf } from '../../utils/assist';
  
      const prefixCls = 'ivu-input-number';
  
      function isValueNumber (value) {
          return (/(^-?[0-9]+\.{1}\d+$)|(^-?[1-9][0-9]*$)/).test(value + '');
      }
      function addNum (num1, num2) {
          var sq1, sq2, m;
          try {
              sq1 = num1.toString().split(".")[1].length;
          }
          catch (e) {
              sq1 = 0;
          }
          try {
              sq2 = num2.toString().split(".")[1].length;
          }
          catch (e) {
              sq2 = 0;
          }
  //        if (sq1 === 0 || sq2 === 0) {
  //            return num1 + num2;
  //        } else {
  //            m = Math.pow(10, Math.max(sq1, sq2));
  //            return (num1 * m + num2 * m) / m;
  //        }
          m = Math.pow(10, Math.max(sq1, sq2));
          return (num1 * m + num2 * m) / m;
      }
  
      export default {
          props: {
              max: {
                  type: Number,
                  default: Infinity
              },
              min: {
                  type: Number,
                  default: -Infinity
              },
              step: {
                  type: Number,
                  default: 1
              },
              value: {
                  type: Number,
                  default: 1
              },
              size: {
                  validator (value) {
                      return oneOf(value, ['small', 'large']);
                  }
              },
              disabled: {
                  type: Boolean,
                  default: false
              }
          },
          data () {
              return {
                  focused: false,
                  upDisabled: false,
                  downDisabled: false
              }        
          },
          computed: {
              wrapClasses () {
                  return [
                      `${prefixCls}`,
                      {
                          [`${prefixCls}-${this.size}`]: !!this.size,
                          [`${prefixCls}-disabled`]: this.disabled,
                          [`${prefixCls}-focused`]: this.focused
                      }
                  ]
              },
              handlerClasses () {
                  return `${prefixCls}-handler-wrap`;
              },
              upClasses () {
                  return [
                      `${prefixCls}-handler`,
                      `${prefixCls}-handler-up`,
                      {
                          [`${prefixCls}-handler-up-disabled`]: this.upDisabled
                      }
                  ]
              },
              innerUpClasses () {
                  return `${prefixCls}-handler-up-inner`;
              },
              downClasses () {
                  return [
                      `${prefixCls}-handler`,
                      `${prefixCls}-handler-down`,
                      {
                          [`${prefixCls}-handler-down-disabled`]: this.downDisabled
                      }
                  ]
              },
              innerDownClasses () {
                  return `${prefixCls}-handler-down-inner`;
              },
              inputWrapClasses () {
                  return `${prefixCls}-input-wrap`;
              }
          },
          methods: {
              preventDefault (e) {
                  e.preventDefault();
              },
              up () {
                  if (this.upDisabled) {
                      return false;
                  }
                  this.changeStep('up');
              },
              down () {
                  if (this.downDisabled) {
                      return false;
                  }
                  this.changeStep('down');
              },
              changeStep (type) {
                  if (this.disabled) {
                      return false;
                  }
  
                  let val = Number(this.value);
                  const step = Number(this.step);
                  if (isNaN(val)) {
                      return false;
                  }
  
                  if (type == 'up') {
                      val = addNum(val, step);
                  } else if (type == 'down') {
                      val = addNum(val, -step);
                  }
                  this.setValue(val);
              },
              setValue (val) {
                  this.value = val;
                  this.$emit('on-change', val);
              },
              focus () {
                  this.focused = true;
              },
              blur () {
                  this.focused = false;
              },
              keyDown (e) {
                  if (e.keyCode === 38) {
                      e.preventDefault();
                      this.up()
                  } else if (e.keyCode === 40) {
                      e.preventDefault();
                      this.down()
                  }
              },
              change (event) {
                  let val = event.target.value.trim();
  
                  const max = this.max;
                  const min = this.min;
  
                  if (isValueNumber(val)) {
                      val = Number(val);
                      if (val > max) {
                          this.setValue(max);
                      } else if (val < min) {
                          this.setValue(min);
                      } else {
                          this.setValue(val);
                      }
                  } else {
                      event.target.value = this.value;
                  }
              }
          },
          watch: {
              value (val) {
                  if (isValueNumber(val) || val === 0) {
                      val = Number(val);
                      const step = this.step;
                      if (val + step > this.max) {
                          this.upDisabled = true;
                      } else if (val - step < this.min) {
                          this.downDisabled = true;
                      } else {
                          this.upDisabled = false;
                          this.downDisabled = false;
                      }
                  } else {
                      this.upDisabled = true;
                      this.downDisabled = true;
                  }
              }
          }
      }
  </script>