rareclass rareclass - 9 months ago 127
Javascript Question

Vue component loses first keypress

I have the following Vue component that displays a save and cancel input group addon when the input changes. Can anyone explain why the keypress is lost from the input when the textChanged value changes and how to fix it, please?

JSFiddle

<div id="app">
<my-input></my-input>
</div>

<template id="my-template">
<div class="form-group">
<label>Test</label>
<div :class="{'input-group': textChanged}">
<input type="text" class="form-control" ref="inp"
@input="updateValue($event.target.value)" :value="value">
<div v-show="textChanged" class="input-group-addon">Save</div>
<div v-show="textChanged" class="input-group-addon" @click="cancel">Cancel</div>
</div>
</div>
</template>


 

new Vue({
el: '#app'
});

Vue.component('my-input', {
template: '#my-template',
props: ['value'],
mounted: function() {
this.original = this.value || "";
},
methods: {
updateValue: function(value) {
this.textChanged = this.$refs.inp.value !== this.original;
this.$emit('input', value);
},
cancel: function() {
this.$refs.inp.value = this.original;
this.textChanged = false;
}
},
data: function() {
return {
original: '',
textChanged: false
}
},
})

Answer Source

So as per @Bert indicated, I need to save the value. This is the final component

<div id="app">
  <my-input @change="save"></my-input>
</div>

<template id="my-template">
  <div class="form-group">
    <label>Test</label>
    <div :class="{'input-group': textChanged}">
      <input type="text" class="form-control" ref="inp" v-model="current">
      <div v-show="textChanged" class="input-group-addon" @click="save">Save</div>
      <div v-show="textChanged" class="input-group-addon" @click="cancel">Cancel</div>
    </div>
  </div>
</template>

 

Vue.component('my-input', {
  template: '#my-template',
  props: ['value'],
  data () {
    return {
        current: "",
        original: ""
    }
  },
  mounted: function() {
    this.current = this.original = this.value || "";
  },
  methods: {
    save: function() {
      this.$emit('change', this.current);
      this.original = this.current;
    },
    cancel: function() {
      this.current = this.original;
    }
  },
  computed: {
    textChanged: function() {
    return this.original !== this.current;
    }
  }

});

new Vue({
  el: '#app',
  methods: {
    save(d) {
      //axios.post(...)
      console.log("saving: " + d)
    }
  }
});
Recommended from our users: Dynamic Network Monitoring from WhatsUp Gold from IPSwitch. Free Download