open-nomad/ui/app/components/stepper-input.js

79 lines
1.7 KiB
JavaScript
Raw Normal View History

2020-06-18 20:19:47 +00:00
import Component from '@ember/component';
import { action } from '@ember/object';
import { debounce } from '@ember/runloop';
import { oneWay } from '@ember/object/computed';
2020-06-19 03:13:36 +00:00
import { classNames, classNameBindings } from '@ember-decorators/component';
2020-06-18 20:19:47 +00:00
import classic from 'ember-classic-decorator';
const ESC = 27;
@classic
@classNames('stepper-input')
2021-12-28 16:08:12 +00:00
@classNameBindings(
'class',
'disabled:is-disabled',
'disabled:tooltip',
'disabled:multiline'
)
2020-06-18 20:19:47 +00:00
export default class StepperInput extends Component {
min = 0;
max = 10;
value = 0;
debounce = 500;
onChange() {}
// Internal value changes immediately for instant visual feedback.
// Value is still the public API and is expected to mutate and re-render
// On onChange which is debounced.
@oneWay('value') internalValue;
@action
increment() {
if (this.internalValue < this.max) {
this.incrementProperty('internalValue');
this.update(this.internalValue);
}
}
@action
decrement() {
if (this.internalValue > this.min) {
this.decrementProperty('internalValue');
this.update(this.internalValue);
}
}
@action
setValue(e) {
if (e.target.value !== '') {
2021-12-28 16:08:12 +00:00
const newValue = Math.floor(
Math.min(this.max, Math.max(this.min, e.target.value))
);
this.set('internalValue', newValue);
this.update(this.internalValue);
} else {
e.target.value = this.internalValue;
}
2020-06-18 20:19:47 +00:00
}
@action
resetTextInput(e) {
if (e.keyCode === ESC) {
e.target.value = this.internalValue;
}
}
@action
selectValue(e) {
e.target.select();
}
2020-06-18 20:19:47 +00:00
update(value) {
debounce(this, sendUpdateAction, value, this.debounce);
}
}
function sendUpdateAction(value) {
return this.onChange(value);
}