Easy Tutorial
❮ Vue3 Class Bind Vue3 V If ❯

Vue3 Forms

In this section, we will introduce the application of forms in Vue.

We can use the v-model directive to create two-way data bindings on form <input>, <textarea>, and <select> elements.

v-model automatically selects the correct method to update the element based on the control type.

v-model ignores the initial values of the value, checked, and selected attributes of all form elements and uses the initial values declared in the data option.

Input Fields

The following example demonstrates two-way data binding using v-model on input and textarea elements:

<div id="app">
  <p>input element:</p>
  <input v-model="message" placeholder="Edit me...">
  <p>input form message is: {{ message }}</p>

  <p>textarea element:</p>
  <textarea v-model="message2" placeholder="Multi-line text input..."></textarea>
  <p>textarea form message is:</p>
  <p style="white-space: pre">{{ message2 }}</p>

</div>

<script>
const app = {
  data() {
    return {
      message: '',
      message2: 'tutorialpro.org\r\nhttps://www.tutorialpro.org'
    }
  }
}

Vue.createApp(app).mount('#app')
</script>
<!-- Incorrect -->
<textarea>{{ text }}</textarea>

<!-- Correct -->
<textarea v-model="text"></textarea>

Checkboxes

A single checkbox binds to a boolean value, while multiple checkboxes bind to the same array:

Checkboxes

The following example demonstrates two-way data binding for checkboxes:

<div id="app">
  <p>Single checkbox:</p>
  <input type="checkbox" id="checkbox" v-model="checked">
  <label for="checkbox">{{ checked }}</label>

  <p>Multiple checkboxes:</p>
  <input type="checkbox" id="tutorialpro" value="tutorialpro" v-model="checkedNames">
  <label for="tutorialpro">tutorialpro</label>
  <input type="checkbox" id="google" value="Google" v-model="checkedNames">
  <label for="google">Google</label>
  <input type="checkbox" id="taobao" value="Taobao" v-model="checkedNames">
  <label for="taobao">taobao</label>
  <br>
  <span>Selected values: {{ checkedNames }}</span>
</div>

<script>
const app = {
  data() {
    return {
      checked : false,
      checkedNames: []
    }
  }
}

Vue.createApp(app).mount('#app')
</script>

Radio Buttons

The following example demonstrates two-way data binding for radio buttons:

Radio Buttons

<div id="app">
  <input type="radio" id="tutorialpro" value="tutorialpro" v-model="picked">
  <label for="tutorialpro">tutorialpro</label>
  <br>
  <input type="radio" id="google" value="Google" v-model="picked">
  <label for="google">Google</label>
  <br>
  <span>Selected value: {{ picked }}</span>
</div>

<script>
const app = {
  data() {
    return {
      picked : 'tutorialpro'
    }
  }
}

Vue.createApp(app).mount('#app')
</script>

Select List

The following example demonstrates two-way data binding for a dropdown list:

Select

<div id="app">
  <select v-model="selected" name="site">
    <option value="">Choose a website</option>
    <option value="www.tutorialpro.org">tutorialpro</option>
    <option value="www.google.com">Google</option>
  </select>

  <div id="output">
       Selected website: {{selected}}
  </div>
</div>

<script>
const app = {
  data() {
    return {
      selected: '' 
    }
  }
}

Vue.createApp(app).mount('#app')
</script>

For multiple selections, it binds to an array:

Select

<div id="app">
  &lt;select v-model="selected" name="fruit" multiple>
    <option value="www.tutorialpro.org">tutorialpro</option>
    <option value="www.google.com">Google</option>
    <option value="www.taobao.com">Taobao</option>
  </select>

  <div id="output">
       Selected websites: {{selected}}
  </div>
</div>

<script>
const app = {
  data() {
    return {
      selected: '' 
    }
  }
}

Vue.createApp(app).mount('#app')
</script>

Using v-for to loop through options:

Select

<div id="app" class="demo">
  <select v-model="selected">
    <option v-for="option in options" :value="option.value">
      {{ option.text }}
    </option>
  </select>
  <span>Selected: {{ selected }}</span>
</div>

<script>
const app = {
  data() {
    return {
      selected: 'www.tutorialpro.org',
      options: [
        { text: 'tutorialpro', value: 'www.tutorialpro.org' },
        { text: 'Google', value: 'www.google.com' },
        { text: 'Taobao', value: 'www.taobao.com' }
      ]
    }
  }
}

Vue.createApp(app).mount('#app')
</script>

Value Binding

For radio buttons, checkboxes, and select options, v-model binding values are usually static strings (or booleans for checkboxes):

<!-- When selected, `picked` is the string "a" -->
<input type="radio" v-model="picked" value="a" />

<!-- `toggle` is true or false -->
<input type="checkbox" v-model="toggle" />

<!-- When the first option is selected, `selected` is the string "abc" -->
<select v-model="selected">
  <option value="abc">ABC</option>
</select>

However, you might want to bind the value to a dynamic property on the current active instance. This can be done with v-bind. Additionally, using v-bind allows binding input values to non-string values.

Checkbox:

<input type="checkbox" v-model="toggle" true-value="yes" false-value="no" />
...
// When checked
vm.toggle === 'yes'
// When unchecked 
vm.toggle === 'no'

Radio:

<input type="radio" v-model="pick" v-bind:value="a" />
// When selected
vm.pick === vm.a

Select Option:

<select v-model="selected">
  <!-- Inline object literal -->
  &lt;option :value="{ number: 123 }">123</option>
</select>
// When selected
typeof vm.selected // => 'object'
vm.selected.number // => 123

Modifiers

.lazy

By default, v-model syncs the input with the data on the input event. You can add a lazy modifier to change this to the change event:

<!-- Sync on "change" instead of "input" -->
&lt;input v-model.lazy="msg" >

.number

To automatically convert user input to a Number type, you can add a number modifier to v-model:

&lt;input v-model.number="age" type="number">

This is often useful because even with type="number", the value from HTML inputs is always a string.

.trim

To automatically trim user input, you can add a trim modifier to v-model:

&lt;input v-model.trim="msg">
❮ Vue3 Class Bind Vue3 V If ❯