《Vue3实战教程》19:Vue3组件 v-model

如果您有疑问,请观看视频教程《Vue3实战教程》

组件 v-model​

基本用法​

v-model 可以在组件上使用以实现双向绑定。

从 Vue 3.4 开始,推荐的实现方式是使用 defineModel() 宏:

vue

<!-- Child.vue -->
<script setup>
const model = defineModel()function update() {model.value++
}
</script><template><div>Parent bound v-model is: {{ model }}</div><button @click="update">Increment</button>
</template>

父组件可以用 v-model 绑定一个值:

template

<!-- Parent.vue -->
<Child v-model="countModel" />

defineModel() 返回的值是一个 ref。它可以像其他 ref 一样被访问以及修改,不过它能起到在父组件和当前变量之间的双向绑定的作用:

  • 它的 .value 和父组件的 v-model 的值同步;
  • 当它被子组件变更了,会触发父组件绑定的值一起更新。

这意味着你也可以用 v-model 把这个 ref 绑定到一个原生 input 元素上,在提供相同的 v-model 用法的同时轻松包装原生 input 元素:

vue

<script setup>
const model = defineModel()
</script><template><input v-model="model" />
</template>

演练场示例

底层机制​

defineModel 是一个便利宏。编译器将其展开为以下内容:

  • 一个名为 modelValue 的 prop,本地 ref 的值与其同步;
  • 一个名为 update:modelValue 的事件,当本地 ref 的值发生变更时触发。

在 3.4 版本之前,你一般会按照如下的方式来实现上述相同的子组件:

vue

<!-- Child.vue -->
<script setup>
const props = defineProps(['modelValue'])
const emit = defineEmits(['update:modelValue'])
</script><template><input:value="props.modelValue"@input="emit('update:modelValue', $event.target.value)"/>
</template>

然后,父组件中的 v-model="foo" 将被编译为:

template

<!-- Parent.vue -->
<Child:modelValue="foo"@update:modelValue="$event => (foo = $event)"
/>

如你所见,这显得冗长得多。然而,这样写有助于理解其底层机制。

因为 defineModel 声明了一个 prop,你可以通过给 defineModel 传递选项,来声明底层 prop 的选项:

js

// 使 v-model 必填
const model = defineModel({ required: true })// 提供一个默认值
const model = defineModel({ default: 0 })

WARNING

如果为 defineModel prop 设置了一个 default 值且父组件没有为该 prop 提供任何值,会导致父组件与子组件之间不同步。在下面的示例中,父组件的 myRef 是 undefined,而子组件的 model 是 1:

子组件:

js

const model = defineModel({ default: 1 })

父组件:

js

const myRef = ref()

html

<Child v-model="myRef"></Child>

v-model 的参数​

组件上的 v-model 也可以接受一个参数:

template

<MyComponent v-model:title="bookTitle" />

在子组件中,我们可以通过将字符串作为第一个参数传递给 defineModel() 来支持相应的参数:

vue

<!-- MyComponent.vue -->
<script setup>
const title = defineModel('title')
</script><template><input type="text" v-model="title" />
</template>

在演练场中尝试一下

如果需要额外的 prop 选项,应该在 model 名称之后传递:

js

const title = defineModel('title', { required: true })

3.4 之前的用法

 

多个 v-model 绑定​

利用刚才在 v-model 的参数小节中学到的指定参数与事件名的技巧,我们可以在单个组件实例上创建多个 v-model 双向绑定。

组件上的每一个 v-model 都会同步不同的 prop,而无需额外的选项:

template

<UserNamev-model:first-name="first"v-model:last-name="last"
/>

vue

<script setup>
const firstName = defineModel('firstName')
const lastName = defineModel('lastName')
</script><template><input type="text" v-model="firstName" /><input type="text" v-model="lastName" />
</template>

在演练场中尝试一下

3.4 之前的用法

 

处理 v-model 修饰符​

在学习输入绑定时,我们知道了 v-model 有一些内置的修饰符,例如 .trim.number 和 .lazy。在某些场景下,你可能想要一个自定义组件的 v-model 支持自定义的修饰符。

我们来创建一个自定义的修饰符 capitalize,它会自动将 v-model 绑定输入的字符串值第一个字母转为大写:

template

<MyComponent v-model.capitalize="myText" />

通过像这样解构 defineModel() 的返回值,可以在子组件中访问添加到组件 v-model 的修饰符:

vue

<script setup>
const [model, modifiers] = defineModel()console.log(modifiers) // { capitalize: true }
</script><template><input type="text" v-model="model" />
</template>

为了能够基于修饰符选择性地调节值的读取和写入方式,我们可以给 defineModel() 传入 get 和 set 这两个选项。这两个选项在从模型引用中读取或设置值时会接收到当前的值,并且它们都应该返回一个经过处理的新值。下面是一个例子,展示了如何利用 set 选项来应用 capitalize (首字母大写) 修饰符:

vue

<script setup>
const [model, modifiers] = defineModel({set(value) {if (modifiers.capitalize) {return value.charAt(0).toUpperCase() + value.slice(1)}return value}
})
</script><template><input type="text" v-model="model" />
</template>

在演练场中尝试一下

3.4 之前的用法

 

带参数的 v-model 修饰符​

这里是另一个例子,展示了如何在使用多个不同参数的 v-model 时使用修饰符:

template

<UserNamev-model:first-name.capitalize="first"v-model:last-name.uppercase="last"
/>

vue

<script setup>
const [firstName, firstNameModifiers] = defineModel('firstName')
const [lastName, lastNameModifiers] = defineModel('lastName')console.log(firstNameModifiers) // { capitalize: true }
console.log(lastNameModifiers) // { uppercase: true }
</script>

3.4 之前的用法vue

<script setup>
const props = defineProps({
firstName: String,
lastName: String,
firstNameModifiers: { default: () => ({}) },
lastNameModifiers: { default: () => ({}) }
})
defineEmits(['update:firstName', 'update:lastName'])console.log(props.firstNameModifiers) // { capitalize: true }
console.log(props.lastNameModifiers) // { uppercase: true }
</script>

在 GitHub 上编辑此页

 前一篇事件下一篇 透传 Attributes

组件 v-model已经加载完毕

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/503112.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

源代码编译安装X11及相关库、vim,配置vim(1)

一、目录结构 如下。 所有X11及相关库装到mybuild&#xff0c;源代码下载到src下&#xff0c;解压&#xff0c;进入&#xff0c;编译安装。编译时指定--prefix到相同的目录&#xff0c;即上图中mybuild。 ./configure --prefixpwd/../../mybuild [CFLAGS"-I/path/to/X11…

图漾相机基础操作

1.客户端概述 1.1 简介 PercipioViewer是图漾基于Percipio Camport SDK开发的一款看图软件&#xff0c;可实时预览相机输出的深度图、彩色图、IR红外图和点云图,并保存对应数据&#xff0c;还支持查看设备基础信息&#xff0c;在线修改gain、曝光等各种调节相机成像的参数功能…

vulnhub靶场-potato(至获取shell)

arp-scan -l 扫描IP 使用御剑端口扫描扫描端口&#xff0c;扫到了80和7120两个端口&#xff0c;其中7120为ssh端口 使用dirb http://192.168.171.134 扫描目录 发现info.php 访问为phpinfo界面 访问192.168.171.134为一个大土豆&#xff0c;没什么用 所以我们从ssh入手 盲…

谈一谈对事件循环的理解

事件循环⼜叫做消息循环&#xff0c;是浏览器渲染主线程的⼯作⽅式。特别是在JavaScript和Node.js等异步编程环境中&#xff0c;也是核心概念之一。它的主要作用是管理异步操作&#xff0c;确保代码的执行顺序和效率。 并且这个话题很有可能是一个面试题。我先把参考答案放下面…

kafka使用以及基于zookeeper集群搭建集群环境

一、环境介绍 zookeeper下载地址&#xff1a;https://zookeeper.apache.org/releases.html kafka下载地址&#xff1a;https://kafka.apache.org/downloads 192.168.142.129 apache-zookeeper-3.8.4-bin.tar.gz kafka_2.13-3.6.0.tgz 192.168.142.130 apache-zookee…

解决 IntelliJ IDEA 中 Tomcat 日志乱码问题的详细指南

目录 前言1. 分析问题原因2. 解决方案 2.1 修改 IntelliJ IDEA 的 JVM 选项2.2 配置 Tomcat 实例的 VM 选项 2.2.1 设置 Tomcat 的 VM 选项2.2.2 添加环境变量 3. 进一步优化 3.1 修改 Tomcat 的 logging.properties3.2 修改操作系统默认编码 3.2.1 Windows 系统3.2.2 Linux …

067B-基于R语言平台Biomod2模型的物种分布建模与数据可视化-高阶课程【2025】

课程培训包含&#xff1a;发票全套软件脚本学习数据视频文件导师答疑 本教程旨在通过系统的培训学习&#xff0c;学员可以掌握Biomod2模型最新版本的使用方法&#xff0c;最新版包含12个模型&#xff08;ANN, CTA, FDA, GAM, GBM, GLM, MARS, MAXENT, MAXNET, RF, SRE, XGBOOST…

【论文复现】改进麻雀搜索算法优化冷水机组的最优负载调配问题

目录 1.摘要2.麻雀搜索算法SSA原理3.改进策略4.结果展示5.参考文献6.代码获取 1.摘要 为了应对暖通空调&#xff08;HVAC&#xff09;系统由于不当负荷分配导致的高能源消耗问题&#xff0c;本文提出了一种改进麻雀搜索算法&#xff08;ISSA&#xff09;。ISSA算法旨在在满足负…

Java实现下载excel模板,并实现自定义下拉框

GetMapping("excel/download")ApiOperation(value "模板下载")public void getUserRecordTemplate(HttpServletResponse response, HttpServletRequest request) throws IOException {OutputStream outputStream response.getOutputStream();InputStream…

UCAS-算法设计与分析(专硕)-复习参考

算法设计与分析&#xff08;专硕&#xff09; 希望对后来者选课 or 复习提供参考 考试时间&#xff1a;2025年1月6日 18:10~21:00 15 个选择、10个填空、10个计算大题 三个小时&#xff0c;手没有停过&#xff0c;不停得在算&#xff0c;好在没有留空&#xff0c;但已知有些内…

什么样的人适合从事FPGA开发的工作?

FPGA开发不仅要求扎实的技术基础&#xff0c;还非常看重团队合作、自信、沟通技巧以及细致入微的工作态度。从业者需具备面对复杂项目的自信&#xff0c;优秀的沟通能力以确保团队协作顺畅&#xff0c;严谨细心以应对精密的硬件设计&#xff0c;以及强烈的责任心来驱动每一个开…

GitLab 创建项目、删除项目

1、创建项目 点击左上角图标&#xff0c;回到首页 点击 Create a project 点击 Create blank project 输入项目名称&#xff0c;点击Create Project 创建成功 2、删除项目 进入项目列表 点击对应项目&#xff0c;进入项目 进入Settings页面 拖到页面底部&#xff0c;展开Adva…

Visual studio code编写简单记事本exe笔记

安装扩展cmake tools c/c c/c Extension pack CMakeLists.txt cmake_minimum_required(VERSION 3.20) project(NotepadApp)set(CMAKE_CXX_STANDARD 17) set(CMAKE_CXX_STANDARD_REQUIRED ON)# Windows specific settings if(WIN32)set(CMAKE_WINDOWS_EXPORT_ALL_SYMBOLS ON)s…

容器技术思想 Docker K8S

容器技术介绍 以Docker为代表的容器技术解决了程序部署运行方面的问题。在容器技术出现前&#xff0c;程序直接部署在物理服务器上&#xff0c;依赖管理复杂&#xff0c;包括各类运行依赖&#xff0c;且易变&#xff0c;多程序混合部署时还可能产生依赖冲突&#xff0c;给程序…

导出中心设计

业务背景 应用业务经常需要导出数据&#xff0c;但是并发的导出以及不合理的导出参数常常导致应用服务的内存溢出、其他依赖应用的崩溃、导出失败&#xff1b;因此才有导出中心的设计 设计思想 将导出应用所需的内存转移至导出中心&#xff0c;将导出的条数加以限制&#xf…

Unity 中计算射线和平面相交距离的原理

有此方法 能够计算射线和平面是否相交以及射线起点到平面交点的距离 代码分析 var dot Vector3.Dot(ray.direction, plane.normal);计算射线和平面法线的点积&#xff0c;如果大于等于0&#xff0c;则说明射线和平面没有相交&#xff0c;否则&#xff0c;说明射线和平面相交…

网络安全抓包

#知识点&#xff1a; 1、抓包技术应用意义 //有些应用或者目标是看不到的&#xff0c;这时候就要进行抓包 2、抓包技术应用对象 //app,小程序 3、抓包技术应用协议 //http&#xff0c;socket 4、抓包技术应用支持 5、封包技术应用意义 总结点&#xff1a;学会不同对象采用…

数学建模入门——描述性统计分析

摘要&#xff1a;本篇博客主要讲解了数学建模入门的描述性统计分析&#xff0c;包括基本统计量的计算、数据的分布形态、数据可视化和相关性分析。 往期回顾&#xff1a; 数学建模入门——建模流程-CSDN博客 数学建模入门——数据预处理&#xff08;全&#xff09;-CSDN博客 …

遗传学的“正反”之道:探寻生命密码的两把钥匙

正向遗传学 & 反向遗传学 在生活中&#xff0c;我们常常会惊叹于孩子与父母外貌、性格上的相似之处&#xff0c;或是疑惑于某些家族遗传病为何代代相传。其实&#xff0c;这些现象背后都隐藏着遗传学的奥秘。遗传学&#xff0c;作为一门探索生物遗传与变异规律的学科&#…

点击主图,触发的是查看产品详情的逻辑

文章目录 1、点击主图&#xff0c;触发的是查看产品详情的逻辑2、点击主图&#xff0c;发送的请求是 productDetail 这个方法3、与主图相关的代码片段 1、点击主图&#xff0c;触发的是查看产品详情的逻辑 点击主图的确不会触发那些物流参数输入框的自动查询。 那些输入框需要…