当前位置: 首页 > news >正文

Vue 组件通信及进阶语法

文章目录

  • 一、scoped 样式冲突
  • 二、data 是一个函数
  • 三、组件通信
    • 1. 父子通信
      • 1.1 props 校验
      • 1.2 props 比较 data
    • 2. 非父子通信
      • 2.1 event bus
      • 2.2 provide-inject
  • 四、进阶语法
    • 1. v-model 详解
    • 2. sync 修饰符
    • 3. ref 和 $refs
    • 4. $nextTick

一、scoped 样式冲突

注意点:
① 结构:只能有一个根元素;
② 样式:组件中定义的样式默认是全局生效的,会影响到所有组件,而 scoped 属性下的样式可以作用于当前组件;
③ 逻辑:el 是根实例所独有的,data 是一个函数。

默认情况下,写在组件中的样式会全局生效,因此很容易造成多个组件之间的样式冲突问题,而组件应该有着自己独立的样式,我们可以给组件加上 scoped 属性,让样式只作用于当前组件。

<style scoped>
</style>

scoped 原理:给当前组件中的所有元素都添加一个自定义属性(data-v-hash),不同的哈希值用于区分不同的组件!

二、data 是一个函数

在一个组件里面,data 选项必须是一个函数,保证每个组件实例维护独立的一份数据对象。 每次创建新的组件实例,都会执行一次 data 函数,得到一个新对象,各个对象之间互不影响。

在这里插入图片描述

在这里插入图片描述
在这里插入图片描述

三个实例对象各自独立,互不影响!

三、组件通信

组件通信就是指组件与组件之间的数据传递。 组件之间的数据是独立的,无法直接访问其他组件的数据,想要用其他组件的数据,就必须要组件通信。

组件关系分为父子关系和非父子关系:

在这里插入图片描述

1. 父子通信

父组件通过 props 将数据传递给子组件,子组件不能直接修改父组件中的数据,而是利用 $emit 通知父组件进行修改更新。

在这里插入图片描述

<!--App.vue-->
<template><div class="App"><Son :title="myTitle" @changeTitle="handleChange"></Son></div>
</template><script>
import Son from './components/Son.vue';
export default {data() {return {myTitle: '栈老师不回家'}},components: {Son},methods: {handleChange(newTitle) {this.myTitle = newTitle}}
}
</script><style scoped>
.App {width: 600px;height: 600px;background-color: rgb(193, 230, 248);margin: 0 auto;padding: 20px;
}
</style>
<!--Son.vue-->
<template><div class="son">{{ title }}<button @click="changeFn">修改</button></div> 
</template><script>
export default {props: ['title'],methods: {changeFn() {this.$emit('changeTitle', '新数据')}}
}
</script><style>
.son {width: 200px;height: 200px;background-color: #f8dd30;margin: 0, auto;
}
</style>

通过自定义属性和自定义事件来实现父子之间的通信。子组件通过 $emit 向父组件发送消息通知,第一个参数是父组件中自定义的监听事件,第二个参数是修改的新数据,父组件通过 @change Title 监听消息,并做出回应,即修改数据。

1.1 props 校验

props 用于向子组件传递数据,并且可以传递任意类型、任意数量的数据。

为了保证组件的正常运行,组件的 props 不可以乱传。我们可以给组件的 props 指定验证要求,不符合要求,控制台就会有错误提示,可以帮助开发者快速发现错误。

① 类型校验

props: {校验的属性名: 类型 //Number、String、Boolean、Array、Object...
}

② 更详细的校验

props: {校验的属性名: {type: 类型, //Number、String、Boolean、Array、Object...required: true, //是否必填default: 默认值, //默认值validator(value) { //value就是传过来的属性名//自定义校验逻辑return true //true通过校验,false不通过校验}}
} 

1.2 props 比较 data

共同点:都可以给组件提供数据。

区别:data 的数据是自己的,可以随便改;props 的数据是外部的,不能直接改,要遵循单向数据流原则,通知其父组件进行修改。

单向数据流:父组件的 props 更新,会单向向下流动,从而影响到子组件。

count++ 是 count 加 1 并重新赋值,会直接修改 count 的值,而 count + 1 并不会重新赋值,count 的值也不会被改变,所以对于 props 里的数据,不要使用 ++,直接让它 + 1 通知父组件即可!

谁的数据谁负责,数据一般提供在公共的父组件中!

2. 非父子通信

2.1 event bus

event bus 用于非父子组件之间,进行简易的消息传递。

① 创建一个双方都能访问到的事件总线(空 Vue 实例)→ utils/EventBus.js

import Vue from 'vue'
const Bus = new Vue()
export default Bus

② A 组件(接收方),监听 Bus 实例的事件

created() {Bus.$on('sendMsg', (msg) => {this.msg = msg})
}

③ B 组件(发送方),触发 Bus 实例的事件

Bus.$emit('sendMsg', '这是一个消息')

发送方发送消息,从而触发 Bus,而接收方时刻监听着 Bus,Bus 一旦被触发,接收方立马就可以接收到消息!

完整代码如下:

//EventBus.js
//创建一个都能访问到的事件总线(空的Vue实例)
import Vue from "vue";
const Bus = new Vue()
export default Bus
//BaseA.vue
<template><div class="baseA">我是A组件(接收方)<div>{{ msg }}</div></div></template><script>import Bus from '@/utils/EventBus';export default {data() {return {msg: ''}},created() {//订阅消息Bus.$on('sendMsg', (msg) => {this.msg = '收到消息了:'+ msg})}}</script><style scoped>.baseA {width: 200px;height: 150px;padding: 10px;margin-top: 10px;border: 3px solid #000;border-radius: 5px;font-size: 20px;}</style>
<template><div class="baseB">我是B组件(发布方)<button @click="publish">发布通知</button></div>
</template><script>
import Bus from '@/utils/EventBus';
export default {methods: {publish() {//发送方通过触发事件的方式发布消息Bus.$emit('sendMsg', '栈老师回家')}}
}
</script><style scoped>
.baseB {width: 200px;height: 150px;padding: 10px;margin-top: 10px;border: 3px solid #000;border-radius: 5px;font-size: 20px;
}
</style>

在这里插入图片描述

在这里插入图片描述

发送方发送的消息,可以被多个接收方订阅!

2.2 provide-inject

跨层级(孙子和爷爷)之间的通信用 provide-inject。

//发送方,爷爷
provide() {return {color: this.color, //简单类型,非响应式userInfo: this.userInfo //复杂类型,响应式}
},
data() {return {color: 'blue',userInfo: {name: '栈老师',age: 20}}
}
//接收方,孙子
inject: ['color', 'userInfo']

使用 provide-inject 共享数据的时候,通常以复杂类型的形式,把数据包装成一个对象进行传递,这样可以保证数据的响应式。

四、进阶语法

1. v-model 详解

原理:v-model 本质上是一个语法糖,例如应用在输入框上,就是 value 属性和事件的合写。

作用:提供数据的双向绑定。

注意:$event 用于在模版中获取事件的形参。

<!--两个input作用一样-->
<div class="App"><input v-model="msg" type="text"><input :value="msg" @input="msg=$event.target.value" type="text">
</div>

$event.target.value 就是输入框中的值!

表单类组件封装

① 父传子:数据应该是父组件 props 传递过来的,v-model 拆解绑定数据。
② 子传父:监听输入,子传父传值给父组件修改。

应用场景举例:此下拉框中所有的数据都来自它的父组件,所以数据是不能直接修改的,子组件中也不能使用 v-model,因为 v-model 会修改数据,解决办法就是拆解 v-model,让 value 和 @change 拆开写。

在这里插入图片描述

<select :value="cityId" @change="handleChange">
...
</select>
props: {cityId: String
},
methods: {handleChange(e) {this.$emit('父组件中的事件名', e.target.value)}
}
<!--父组件接收-->
<BaseSelect :cityId="selectId" @事件名="selectId=$event"/>

2. sync 修饰符

作用:可以实现子组件与父组件数据的双向绑定,简化代码。

特点:props 属性名可以自定义,非固定为 value。

场景:封装弹框类的基础组件,visible 属性,true 显示,false 隐藏。

:属性名.sync,本质上就是 :属性名和 @update:属性名的合写。

<!--父组件与子组件通过:visible.sync即可实现数据的双向绑定-->
<BaseDialog :visible.sync = "isShow"/>
//子组件正常用props接收数据,emit发出修改申请
props: {visible: Boolean
},
methods: {close() {this.$emit('update:visible', false) //'update:属性名', 修改后的数据}
}

3. ref 和 $refs

作用:ref 和 $refs 用于获取 dom 元素或组件实例。

查询范围:当前组件内(更精准确定)。

① 获取 dom 元素

<!--给目标标签添加ref属性-->
<div ref="chartRef">我是渲染图标的容器</div>
//dom渲染完成后(mounted),通过this.$refs.属性值,获取目标标签
mouted() {console.log(this.$refs.chartRef)
}

② 获取组件

<!--给目标组件添加ref属性-->
<BaseForm ref="baseForm">我是一个组件</BaseForm>
//使用this.$refs.baseForm可以获取目标组件
this.$refs.baseForm.组件方法()

获取到目标组件后,就可以直接调用组件对象里面的方法!

4. $nextTick

需求:点击编辑,编辑框自动显示并聚焦。

this.isShowEdit = true //显示输入框
this.$refs.inp.focu() //获取焦点

问题:以上代码并不能立刻获取焦点。

原因Vue 是异步更新(提升性能)。并不会读一行就执行一行,它要等全部代码都读完了才开始执行,所以此处 dom 还没更新出来,就去获取焦点,显然是不可能成功的。

$nextTick:等 DOM 更新后,才会触发执行此方法里的函数体。

将获取焦点的操作放在 $nextTick 里面就可以了:

this.$nextTick(() => {this.$refs.inp.focus()
})

相关文章:

Vue 组件通信及进阶语法

文章目录 一、scoped 样式冲突二、data 是一个函数三、组件通信1. 父子通信1.1 props 校验1.2 props 比较 data 2. 非父子通信2.1 event bus2.2 provide-inject 四、进阶语法1. v-model 详解2. sync 修饰符3. ref 和 $refs4. $nextTick 一、scoped 样式冲突 注意点&#xff1a;…...

vue文本高亮处理

在vue的v-for循环中处理搜索关键字高亮问题&#xff0c;通过截取文字判断&#xff0c;分成三段拼接起来 <div class"check-list" v-if"shopList.length >0"><a-checkbox change"onChangeShop($event,item)" :checked"checkedL…...

androidstudio入门到放弃配置

b站视频讲解传送门 android_studio安装包&#xff1a;https://developer.android.google.cn/studio?hlzh-cn 下载安装 开始创建hello-world 1.删除缓存 文件 下载gradle文件压缩&#xff1a;gradle-8.9用自己创建项目时自动生成的版本即可&#xff0c;不用和我一样 https://…...

NLP论文速读(谷歌出品)|缩放LLM推理的自动化过程验证器

论文速读|Rewarding Progress: Scaling Automated Process Verifiers for LLM Reasoning 论文信息&#xff1a; 简介&#xff1a; 这篇论文探讨了如何提升大型语言模型&#xff08;LLM&#xff09;在多步推理任务中的性能。具体来说&#xff0c;它试图解决的问题是现有的基于结…...

【Linux学习】【Ubuntu入门】1-4 ubuntu终端操作与shell命令1

1.使用快捷键CtrlAltT打开命令终端&#xff0c;或者单击右键点击… 2.常用shell命令 目录信息查看命令&#xff1a;ls ls -a&#xff1a;显示目录所有文件及文件夹&#xff0c;包括隐藏文件&#xff0c;比如以.开头的 ls -l&#xff1a;显示文件的详细信息 ls -al&#xff1…...

【Qt】Qt在窗口中加载Web界面的方法汇总

1、Qt WebEngine 1)Qt版本:Qt5.4以上; 2)平台要求(https://doc.qt.io/archives/qt-5.9/qtwebengine-platform-notes.html): 例如:Windows下只能使用 MSVC 编译器,不支持MinGW编译器,会报错(: error: Unknown module(s) in QT: webenginewidgets) 并且不能用在Qt编…...

Java集合框架之Collection集合遍历

引言 在Java编程中&#xff0c;集合&#xff08;Collection&#xff09;框架是处理对象集合的核心工具。它提供了一套统一的接口和类来存储和操作对象集合。遍历集合是日常开发中的一项基本任务&#xff0c;本文将深入探讨Java Collection集合的遍历方法&#xff0c;并提供实际…...

基于STM32的智能充电桩:集成RTOS、MQTT与SQLite的先进管理系统设计思路

一、项目概述 随着电动车的普及&#xff0c;充电桩作为关键基础设施&#xff0c;其智能化、网络化管理显得尤为重要。本项目旨在基于STM32微控制器开发一款智能充电桩&#xff0c;能够实现高效的充电监控与管理。项目通过物联网技术&#xff0c;提供实时数据监测、远程管理、用…...

windows 查看yolo11 是否安装了cuda

一、通过python查看 import torch print(torch.cuda.is_available()) 二、通过 pip list 查看 在conda环境 可以看出torch 后面是2.1.4 cu124 说明GPU环境安装成功。 如果是cpu环境&#xff0c;则是&#xff1a;...

机器学习【激活函数】

笔记内容侵权联系删 激活函数的概念神经网络中的每个神经元节点接受上一层神经元的输出值作为本神经元的输入值&#xff0c;并将输入值传递给下一层&#xff0c;输入层神经元节点会将输入属性值直接传递给下一层(隐层或输出层)。在多层神经网络中&#xff0c;上层节点的输入在加…...

【OpenEuler】配置虚拟ip

OpenEuler系统手动配置虚ip 介绍操作方法临时生效永久生效 验证 介绍 我们知道通过keepalived服务可以为linux服务器设置虚拟ip&#xff0c;但是有些特殊场景下若无法安装部署keepalived服务&#xff0c;则需要通过手动设置的方式&#xff0c;配置服务器的虚拟ip。 本方案提供…...

数据分析师证书怎么考

在信息技术飞速发展的今天&#xff0c;数据分析已成为推动各行业进步的核心引擎。CDA&#xff08;Certified Data Analyst&#xff09;数据分析师证书以其权威性和实用性&#xff0c;成为许多数据分析从业者的职业加速器。本文将深入探讨如何考取CDA数据分析师证书&#xff0c;…...

【人工智能】text2vec-large-chinese模型搭建本地知识库

本demo使用 text2vec-large-chinese 模型进行文本处理&#xff0c;然后再过 bge-reranker-v2-m3进行增强 1. 对文本进行向量处理&#xff0c;并保存只至本地 from sentence_transformers import SentenceTransformer import torch import numpy as np import faiss import os …...

前端入门一之ES6--递归、浅拷贝与深拷贝、正则表达式、es6、解构赋值、箭头函数、剩余参数、String、Set

前言 JS是前端三件套之一&#xff0c;也是核心&#xff0c;本人将会更新JS基础、JS对象、DOM、BOM、ES6等知识点&#xff0c;这篇是ES6;这篇文章是本人大一学习前端的笔记&#xff1b;欢迎点赞 收藏 关注&#xff0c;本人将会持续更新。 文章目录 10、递归10.1、阶层案例10.…...

DevOps工程技术价值流:加速业务价值流的落地实践与深度赋能

DevOps的兴起&#xff0c;得益于敏捷软件开发的普及与IT基础设施代码化管理的革新。敏捷宣言虽已解决了研发流程中的诸多挑战&#xff0c;但代码开发仅是漫长价值链的一环&#xff0c;开发前后的诸多问题仍亟待解决。与此同时&#xff0c;虚拟化和云计算技术的飞跃&#xff0c;…...

IP数据云 识别和分析tor、proxy等各类型代理

在网络上使用代理&#xff08;tor、proxy、relay等&#xff09;进行访问的目的是为了规避网络的限制、隐藏真实身份或进行其他的不正当行为。 对代理进行识别和分析可以防止恶意攻击、监控和防御僵尸网络和提高防火墙效率等&#xff0c;同时也可以对用户行为进行分析&#xff…...

vue2 自动化部署 shell 脚本

需求场景&#xff1a;在云平台中进行开发时&#xff0c;由于无法连接外网&#xff0c;在部署前端项目时&#xff0c;是通过本地打包再上传到服务器的方式进行部署的。基于这种部署场景&#xff0c;通过 shell 脚本进行部署流程优化&#xff0c;具体如下&#xff1a; 1、服务器…...

服务器数据恢复——Ext4文件系统使用fsck后mount不上的数据恢复案例

关于Ext4文件系统的几个概念&#xff1a; 块组&#xff1a;Ext4文件系统的全部空间被划分为若干个块组&#xff0c;每个块组结构基本上相同。 块组描述符表&#xff1a;每个块组都对应一个块组描述符&#xff0c;这些块组描述符统一放在文件系统的前部&#xff0c;称为块组描述…...

CTF攻防世界小白刷题自学笔记14

fileclude&#xff0c;难度&#xff1a;1&#xff0c;方向&#xff1a;Web 题目来源:CTF 题目描述:好多file呀&#xff01; 给一下题目链接&#xff1a;攻防世界Web方向新手模式第17题。 打开一看&#xff0c;这熟悉的味道&#xff0c;跟上一篇文章基本一摸一样的&#xff…...

家政服务小程序,家政行业数字化发展下的优势

今年以来&#xff0c;家政市场需求持续增长&#xff0c;市场规模达到了万亿级别&#xff0c;家政服务行业成为了热门行业之一&#xff01; 家政服务种类目前逐渐呈现了多样化&#xff0c;月嫂、保姆、做饭保洁、收纳、维修等家政种类不断出现&#xff0c;满足了居民日益增长的…...

Springboot如何打包部署服务器

文章目的&#xff1a;java项目打包成jar包或war包&#xff0c; 放在服务器上去运行 一、编写打包配置 1. pom.xml 在项目中的pom.xml文件里面修改<build>...</build>的代码 >> 简单打包成Jar形式&#xff0c;参考示例&#xff1a; <build><fina…...

ubuntu将firewall-config导出为.deb文件

firewall-config ubuntu是canonial 公司维护的&#xff0c;用wireshark测过&#xff0c;开机会给他们公司发遥测&#xff08;开了ufw阻塞所有连接也一样&#xff0c;canonial在里面把代码改了&#xff09;firewall-config是fedora(爱好者维护&#xff0c;公益版本)自带的防火墙…...

C++算法练习-day40——617.合并二叉树

题目来源&#xff1a;. - 力扣&#xff08;LeetCode&#xff09; 题目思路分析 题目&#xff1a;给定两棵二叉树 root1 和 root2&#xff0c;请合并这两棵树&#xff0c;即将 root2 中的每个节点合并到 root1 中&#xff0c;合并的规则是如果两个节点在同一位置&#xff08;即…...

2024数维杯国际赛C题【脉冲星定时噪声推断和大气时间信号的时间延迟推断的建模】思路详解

脉冲星是快速旋转的中子星&#xff0c;具有连续和稳定的旋转&#xff0c;因此被称为“宇宙的灯塔”。对脉冲星的空间观测在深空航天器导航和时间标准的维护中起着关键作用。 将脉冲星时间应用于原子时间的保持&#xff0c;预期可以提高本地原子钟的稳定性和可靠性&#xff0c;代…...

【Linux】MTD 分区

我在文章 计算机储存与分区 中讲了关于 GUID 分区和 MBR 分区&#xff0c;他们在 PC 上很常见&#xff0c;但是在嵌入式系统上&#xff0c;Linux 会使用 MTD 分区&#xff0c;至于什么是 MTD 分区&#xff0c;请看&#xff1a; NAND/MTD/UBI/UBIFS概念及使用方法 General MTD…...

MySQL(5)【数据类型 —— 字符串类型】

阅读导航 引言一、char&#x1f3af;基本语法&#x1f3af;使用示例 二、varchar&#x1f3af;基本语法&#x1f3af;使用示例 三、char 和 varchar 比较四、日期和时间类型1. 基本概念2. 使用示例 五、enum 和 set&#x1f3af;基本语法 引言 之前我们聊过MySQL中的数值类型&…...

【数据搜集】初创企业获客,B端数据获取

在竞争激烈的商业世界中&#xff0c;初创企业面临着诸多挑战&#xff0c;而获取 B 端客户资源无疑是其中的关键一环。今天&#xff0c;就让我们深入了解一款专为解决此类难题而生的强大工具 —— 探商宝。 对于初创企业来说&#xff0c;B 端客户往往具有更高的价值和稳定性&am…...

hhdb数据库介绍(9-13)

函数与操作符 计算节点对函数的支持 此文档仅列出部分经特殊处理的函数&#xff0c;若需要了解所有计算节点支持的函数&#xff0c;请向官方获取《计算节点最新功能清单》。 函数名称支持状态是否拦截说明ABS()支持否ACOS()支持否ADDDATE()支持否ADDTIME()支持否AES_DECRYPT…...

Jmeter基础篇(24)Jmeter目录下有哪些文件夹是可以删除,且不影响使用的呢?

一、前言 Jmeter使我们日常做性能测试最常用的工具之一啦&#xff01;但是我们在和其他同学协同工作的时候&#xff0c;偶尔也会遇到一些问题&#xff0c;例如我想要给别人发送一个Jmeter工具包&#xff0c;但这个文件包往往会很大&#xff0c;比较浪费流量和空间&#xff0c;…...

卷积、频域乘积和矩阵向量乘积三种形式之间的等价关系与转换

线性移不变系统 线性移不变系统&#xff08;Linear Time-Invariant System, LTI系统&#xff09;同时满足线性和时不变性两个条件。 线性&#xff1a;如果输入信号的加权和通过系统后&#xff0c;输出是这些输入信号单独通过系统后的输出的相同加权和&#xff0c;那么该系统就…...