表单处理
表单元素的数据绑定
下面是一个文本框和数据进行绑定的例子:
vue
<template>
<input
type="text"
:value="textContent"
@input="(e) => (textContent = e.target.value)"
/>
<p>你当前输入的内容为:{{ textContent }}</p>
</template>
<script setup>
import { ref } from "vue";
const textContent = ref("");
</script>
<style scoped></style>
上面的例子我们让文本库和 ref 数据进行了绑定,用户在输入内容的时候,会去更新 textContent 这个 ref 数据,而 ref 数据的变化又会影响文本框本身的 value 值。这其实就是一个双向绑定的例子。
v-model
上面的例子虽然实现了双向绑定,但是写起来比较麻烦,因此 Vue 提供了一个内置的指令 v-model
vue
<template>
<input type="text" v-model="textContent" />
<p>你当前输入的内容为:{{ textContent }}</p>
</template>
<script setup>
import { ref } from "vue";
const textContent = ref("");
</script>
<style scoped></style>
上面的例子使用了 v-model 来进行双向绑定,textContent 的变化会影响文本框的值,文本框的值也会影响 textContent.
使用 v-model 的好处在于:
- 简化了书写
- 根据所使用的元素自动的选择对应的属性以及事件组合
- input 或者 textarea,元素会绑定 input 事件,绑定的值是 value
- 如果是单选框或者复选框,背后绑定的事件是 change 事件,绑定的值 checked
- select 下拉列表绑定的也是 change 事件,绑定的值是 value
文本域
文本域就是多行文本,对应的标签为 textarea
vue
<template>
<textarea cols="30" rows="10" v-model="textContent"></textarea>
<p>你当前输入的内容为:{{ textContent }}</p>
</template>
<script setup>
import { ref } from "vue";
const textContent = ref("");
</script>
<style scoped></style>
复选框
单一的复选框,可以使用 v-model 去绑定一个 ref 类型的布尔值,布尔值为 true 表示选择中,false 表示未选中
vue
<template>
<input type="checkbox" v-model="checked" />
<button @click="checked = !checked">切换选中</button>
</template>
<script setup>
import { ref } from "vue";
const checked = ref(true);
</script>
<style scoped></style>
在上面的例子中,布尔值 true 是选中,false 是未选中,但是这个真假值是可以自定义:
vue
<template>
<input
type="checkbox"
v-model="checked"
:true-value="customTrue"
:false-value="customFalse"
/>
<button @click="toggle">切换选中</button>
</template>
<script setup>
import { ref } from "vue";
const checked = ref("yes");
// 现在相当于是自定义什么值是选中,什么值是未选中
// 之前是默认true是选中,false是未选中
// 现在是yes是选中,no是未选中
const customTrue = ref("yes");
const customFalse = ref("no");
function toggle() {
checked.value === "yes" ? (checked.value = "no") : (checked.value = "yes");
}
</script>
<style scoped></style>
有些时候我们有多个复选框,这个时候,可以将多个复选框绑定到同一个数组或者集合的值:
vue
<template>
<div v-for="(item, index) in arr" :key="index">
<label for="item.id">{{ item.title }}</label>
<input type="checkbox" v-model="hobby" :id="item.id" :value="item.value" />
</div>
<p>{{ message }}</p>
</template>
<script setup>
import { ref, computed } from "vue";
const hobby = ref([]);
const arr = ref([
{ id: "swim", title: "游泳", value: "游个泳" },
{ id: "run", title: "跑步", value: "跑个步" },
{ id: "game", title: "游戏", value: "玩个游戏" },
{ id: "music", title: "音乐", value: "听个音乐" },
{ id: "movie", title: "电影", value: "看个电影" },
]);
const message = computed(() => {
// 根据 hobby 的值进行二次计算
if (hobby.value.length === 0) return "请选择爱好";
else return `您选择了${hobby.value.join("、")}`;
});
</script>
<style scoped></style>
在上面的例子中,checkbox 所绑定的数据不再是一个布尔值,而是一个数组(集合),那么当该复选框被选中的时候,该复选框所对应的值就会被加入到数组里面。
单选框
vue
<template>
<label for="male">男</label>
<input type="radio" id="male" v-model="gender" value="男" />
<label for="female">女</label>
<input type="radio" id="female" v-model="gender" value="女" />
<label for="secret">保密</label>
<input type="radio" id="secret" v-model="gender" value="保密" />
</template>
<script setup>
import { ref } from "vue";
const gender = ref("保密");
setTimeout(() => {
gender.value = "男";
}, 3000);
</script>
<style scoped></style>
上面的例子演示了单选框如何进行双向绑定,哪一个单选框被选中取决于 gender 的值。
下拉列表
下拉列表在进行双向绑定的时候,v-model 是写在 select 标签上面:
vue
<template>
<!-- 下拉列表列表是单选的话,v-model 绑定的值是一个字符串,这个字符串是 option 的 value 值 -->
<select v-model="hometown1">
<option value="" disabled>请选择</option>
<option
v-for="(item, index) in hometownList"
:key="index"
:value="item.key"
>
{{ item.value }}
</option>
</select>
<p>您选择的家乡为:{{ hometown1 }}</p>
<!-- 如果下拉列表是多选的话,v-model 绑定的值是一个数组,这个数组是 option 的 value 值组成的数组 -->
<select v-model="hometown2" multiple>
<option value="" disabled>请选择</option>
<option
v-for="(item, index) in hometownList"
:key="index"
:value="item.key"
>
{{ item.value }}
</option>
</select>
<p>您选择的家乡为:{{ hometown2 }}</p>
</template>
<script setup>
import { ref } from "vue";
const hometown1 = ref("");
const hometown2 = ref([]);
const hometownList = ref([
{ key: "成都", value: "成都" },
{ key: "帝都", value: "北京" },
{ key: "魔都", value: "上海" },
{ key: "妖都", value: "广州" },
{ key: "陪都", value: "重庆" },
]);
</script>
<style scoped></style>
注意下拉列表根据是单选还是多选,v-model 所绑定的值的类型不一样,单选绑定字符串,多选绑定数组。
v-model 表单修饰符
- lazy:默认情况下,v-model 会在每次 input 事件触发时就更新数据,lazy 修饰符可以改为 change 事件触发后才更新数据
- number:将用户输入的内容从字符串转为 number 类型
- trim:去除输入的内容的两端的空格
vue
<template>
<!-- lazy修饰符演示 -->
<input type="text" v-model.lazy="mess1" />
<p>你输入的是:{{ mess1 }}</p>
<p>类型为{{ typeof mess1 }}</p>
<p>长度为{{ mess1.length }}</p>
<!-- number修饰符演示 -->
<input type="text" v-model.number="mess2" />
<p>你输入的是:{{ mess2 }}</p>
<p>类型为{{ typeof mess2 }}</p>
<p>长度为{{ mess2.length }}</p>
<!-- trim修饰符演示 -->
<input type="text" v-model.trim="mess3" />
<p>你输入的是:{{ mess3 }}</p>
<p>类型为{{ typeof mess3 }}</p>
<p>长度为{{ mess3.length }}</p>
</template>
<script setup>
import { ref } from "vue";
const mess1 = ref("");
const mess2 = ref("");
const mess3 = ref("");
</script>
<style scoped></style>
-EOF-