Search code examples
vue.jsnuxt.jsbuefy

Select is not updating after on change


I'm using Nuxt.js with Buefy and have a select dropdown with options. I have reactivity using v-model and @input.native="options(selectedOptions.windowsLicence)", however I'm now trying to add the data to an order object. So it's showing the last selection value on change, rather than it's updated one, even though my v-model gets updated.

Do I need to put a watcher on this or can I somehow do it within a computed method?

Methods

       options(val){
            let selectedOption = {
                id:'54',
                title: this.selectedOptions.windowsLicence.label,
                price: this.selectedOptions.windowsLicence.price
            }
            this.order.windowsLicence = selectedOption;
        },

Dropdown

 <b-field class="pt-3">
    <b-select 
       placeholder="None - $0.00"
       expanded
       @input.native="options(selectedOptions.windowsLicence)"
       v-model="selectedOptions.windowsLicence"
       icon="windows"
       icon-pack="fab"
       size="is-medium">
       <optgroup>
            <option v-for="(licence, key, index) in serverOptions.windowsLicences" :key="index" :value="{ 'id':licence.id, 'label':licence.label, 'price':licence.price }">{{licence.label}} - ${{licence.price}}.00</option>
        </optgroup>
     </b-select>
 </b-field>

Data Property - Has Reactivity

{{selectedOptions.windowsLicence}}

Adding to the order is 1 step behind in the selection

{{order}}

Solution

  • v-model is a shortcut for adding both @input and :value in one directive.

    Docs: https://v2.vuejs.org/v2/guide/components.html#Using-v-model-on-Components.

    Adding .native to an event handler means listening to actual DOM element event not Vue component event.

    <b-select /> renders a <div> which doesn't have an input event.

    Say you are interested if <b-select /> is clicked.

    <b-select /> does not $emit('click') event so you cannot do @click="doSomethingWhenClicked"

    that's when you use <b-select @click.native="doSomethingWhenClicked" />


    To answer how you can react to value selected,

    you can either do watcher or methods.

    Watcher

    <template>
      <b-select v-model="selected" />
    </template>
    
    <script>
      ...
      data() {
        return {
          selected: null
        }
      },
    
      watch: {
        selected(newValue, oldValue) {
          // Do something here
        }
      }
    </script>
    

    Methods

    <template>
      <b-select :value="selected" @input="onSelect" />
    </template>
    
    <script>
      ...
      data() {
        return {
          selected: null
        }
      },
    
      methods: {
        onSelect(selectedValue) {
          this.selected = selectedValue
          // Do something here
        }
      }
    </script>