Vue3 ~

news2024/11/22 14:09:22

变动

  • 实例
const app = new Vue({})
Vue.use()
Vue.mixin()
Vue.component()
Vue.directive()
const app = Vue.createApp({})
app.use()
app.mixin()
app.component()
app.directive()
  • createApp 代替 new Vue

在这里插入图片描述

  • 允许多个根标签

在这里插入图片描述

  • createStore 代替 Vue.use(Vuex)

在这里插入图片描述

  • createRouter 代替 Vue.use(VueRouter)

在这里插入图片描述

  • 动画
 - v-enter --- v-enter-from
 - v-leave-to  --- vl-eave-to 
 - v-leave  ---  v-leave-from
 - v-enter-to  --- v-enter-to
  • 移除过滤器 filter、keyCode、v-on.native

新特性

  • 组合式 API :定义的数据和使用一并进行处理,达到易读,更便捷、更好的代码组织效果
  • **** options api 对应 react class component
  • **** composition api 对应 react hooks,setup 只会调用一次,hooks 可多次调用
  • 响应式变更:使用 Proxy 代替 Object.defineProperty
  • 全新的全家桶:vue-router、vuex、pinia 等周边库更新
  • TypeScript 支持
  • Vite 支持:依赖于 es module 导致无法直接对 commonJS 的模块化方式进行支持。必须采用依赖预构建

setup

  • options api 中的 data methods computed… 可以发访问setup中的属性和方法
  • setup中不能访问options api中的 data methods computed…
  • 返回一个对象或渲染函数(render 函数)、两个参数:props:参数、context:上下文( attrs, slots, emit )
setup(props, { attrs, slots, emit }) {
	return {}
}
  • thisundefined ,通过 getCurrentInstance 获取实例
import { getCurrentInstance } from 'vue'
const instance = getCurrentInstance()

生命周期

  • beforeDestroy —> beforeUnmount
  • destroyed —> unmounted
  • setup 等于 beforeCreate 和 created
import {
  onBeforeMount,
  onMounted,
  onBeforeUpdate,
  onUpdated,
  onBeforeUnmount,
  onUnmounted
} from 'vue'

ref、reactive

  • reference对象:创建一个包含响应式的引用对象,接受类型可以是基本类型,也可以是对象类型,除了 template 和reactive,需通过.value修改其值;
  • 响应式实现:基本类型依赖于Object.defineProperty,对象依赖于proxy
<template>
  <p ref="elemRef">文字</p>
</template>
<script setup>
import { ref, onMounted } from 'vue'
const elemRef = ref(null)
onMounted(() => {
  console.log(elemRef.value)
})
</script>
  • reactive:定义一个引用类型响应式数据,不能使用基本类型,解构 reactive 的值会失去响应式
import { ref, reactive } from 'vue'
const nameRef = ref('张三')
const state = reactive({
  name: nameRef
})
</script>

toRef、toRefs

  • toRef:针对一个响应式对象(reactive封装)的属性,创建一个ref类型并且两者保持引用关系;
<script setup>
import { toRef, reactive } from 'vue'
const state = reactive({
  age: 20,
  name: '张三'
})
const ageRef = toRef(state, 'age')
</script>
  • toRefs:将响应式对象(reactive封装)转换为普通对象,对象中的每个属性都是ref,两者保持引用关系
<script setup>
import { toRefs, reactive } from 'vue'
function useFeatureX() {
  const state = reactive({
    x: 1,
    y: 2
  })
  return toRefs(state)
}
const { x, y } = useFeatureX()
</script>

emits

  • 自定义事件需要进行声明
<HelloWorld @onSayHello="sayHello" />
export default {
  emits: ['onSayHello'],
  setup(props, { emit }) {
    emit('onSayHello', '内容')
  }
}
  • 多事件
<button @click="one($event) two($event)">click</button>

watch、watchEffect

  • watch:监听值、处理函数、配置项
  • ref 类型 newValue, oldValue 不需要 .value
  • 引用类型数据设置深度监视无法正确的获取 oldValue
  • reactive 使用函数形式
import { watch } from 'vue'

watch(
  data, // 监听一个基本类型
  // [data1,data2], // 监听多个 ref 基本属性
  // objdata, // ref 引用类型
  (newValue, oldValue) => {},
  { immediate: true } // 初始化监听
)

watch(
  () => obj.xx, // 监听一个 reactive
  // [ () => obj1.xx, () => obj2.xx ], // 监听多个 reactive
  (newValue, oldValue) => {},
  // { immediate: true , deep: true} // 引用类型设置深度监视
)
  • watchEffect:不用指明监视属性,回调中用到什么属性即监视什么属性,默认开启 immediate:true
import { watchEffect } from 'vue'
watchEffect(() => {
  // ...
})

v-model 自定义

  • 父组件
<my-input v-model="val" />
const val = ref('hello')
  • 子组件
props: {
  modelValue: String
},
const handler = (e: Event) => {
  const targetValue = (e.target as HTMLInputElement).value
  context.emit('update:modelValue', targetValue) // 相当于自定义modal $emit
}

.sync

  • vue2.x
<myComponent v-bind:age.sync="age"></myComponent>
  • vue3.x
<template>
  <p>{{ age }}</p>
  <user-info v-model:ageRef="age"></user-info>
</template>

<script>
import { reactive, toRefs } from 'vue'
import UserInfo from './UserInfo.vue'

export default {
  name: 'VModel',
  components: { UserInfo },
  setup() {
    const state = reactive({
      age: '20'
    })
    return toRefs(state)
  }
}
</script>
<template>
  <input :value="ageRef" @input="$emit('update:ageRef', $event.target.value)" />
</template>

<script>
export default {
  name: 'UserInfo',
  props: {
    ageRef: String
  }
}
</script>

异步组件

vue2.x

components:{
	'my-component':() => import('./xx.vue')
}

vue3.x

import { defineAsyncComponent } from 'vue'
components:{
	AsyncComponent: defineAsyncComponent(() => import('./xx.vue'))
}

Teleport

直接将元素插入到某个节点之中

<teleport to="body">
	...
</teleport>

Suspense

用于实现异步,组件内部有两个插槽。

<Suspense>
	<template>
		<AsyncComponent/>
	</template>
	<template #fallback>
		<span>loading...</span>
	</template>
</Suspense>

Vue3.3

  • defineModel

before:

// 1
defineProps({
  modelValue: {
    type: Number,
    required: true,
    default: 0
  }
})
// 2
defineProps(['modelValue']) 

now:

const modelValue = defineModel<number>({ default: 0 })
  • defineEmits

before:

const emits = defineEmits<
  SE<{
    clickCount(num: number): void
  }>
>()
const emits = defineEmits<{
  (e: 'clickCount', num: number): void
}>()

now:

const emits = defineEmits<{
  clickCount: [num: number]
}>()

Vue3为何更快

  • Proxy 响应式
  • PatchFlag:编译模板时动态节点会做标记,标记分为不同类型,diff 算法可以区分静态节点以及不同类型的动态节点;
<div>
  <span>hello</span>
  <span>{{ name }}</span>
  <span :class="blue">张三</span>
  <span :id="zhangsan">张三</span>
  <span :id="lisi" :class="black">{{ obj.name }}</span>
</div>
import { createElementVNode as _createElementVNode, toDisplayString as _toDisplayString, normalizeClass as _normalizeClass, openBlock as _openBlock, createElementBlock as _createElementBlock } from "vue"

export function render(_ctx, _cache, $props, $setup, $data, $options) {
  return (_openBlock(), _createElementBlock("div", null, [
    _createElementVNode("span", null, "hello"),
    _createElementVNode("span", null, _toDisplayString(_ctx.name), 1 /* TEXT */),
    _createElementVNode("span", {
      class: _normalizeClass(_ctx.blue)
    }, "张三", 2 /* CLASS */),
    _createElementVNode("span", { id: _ctx.zhangsan }, "张三", 8 /* PROPS */, ["id"]),
    _createElementVNode("span", {
      id: _ctx.lisi,
      class: _normalizeClass(_ctx.black)
    }, _toDisplayString(_ctx.obj.name), 11 /* TEXT, CLASS, PROPS */, ["id"])
  ]))
}

以上TEXT 、PROPS 、CLASS 则为标记的不同类型,只会去比较有标记的区域,静态则不会进行对比。

在这里插入图片描述

  • hoistStatic:静态节点的定义提升到父作用域进行缓存,多个相邻的静态节点会被合并起来,拿空间换时间;
  • cacheHandler:缓存事件
  • SSR 优化
  • tree-shaking:模板编译会根据不同情况引入不同的API

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

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

保障网络安全:IP代理识别API的作用与应用

引言 随着互联网的不断发展&#xff0c;网络安全问题已经变得愈发重要。在网络上&#xff0c;恶意用户可以利用IP代理隐藏其真实身份&#xff0c;从而发动各种网络攻击或欺诈行为。为了保障网络安全&#xff0c;IP代理识别API成为了一种不可或缺的工具&#xff0c;本文将深入探…

计算机竞赛 深度学习 opencv python 公式识别(图像识别 机器视觉)

文章目录 0 前言1 课题说明2 效果展示3 具体实现4 关键代码实现5 算法综合效果6 最后 0 前言 &#x1f525; 优质竞赛项目系列&#xff0c;今天要分享的是 &#x1f6a9; 基于深度学习的数学公式识别算法实现 该项目较为新颖&#xff0c;适合作为竞赛课题方向&#xff0c;学…

Apollo配置更新通知

文章目录 启用方式hook编写服务部署本地部署容器化部署构建镜像 使用 ⚡️: 应领导要求想要把 Apollo 配置变更信息更新到企业微信群中&#xff0c;线上出现异常可根据变更时间&#xff0c;快速反应是否是配置变更导致异常 启用方式 &#x1f31b;: 前提有一个可正常使用的Apo…

微服务保护-Sentinel

初识Sentinel 雪崩问题及解决方案 雪崩问题 微服务中&#xff0c;服务间调用关系错综复杂&#xff0c;一个微服务往往依赖于多个其它微服务。 如图&#xff0c;如果服务提供者I发生了故障&#xff0c;当前的应用的部分业务因为依赖于服务I&#xff0c;因此也会被阻塞。此时&a…

深度学习pytorch之tensorboard和transform的使用

这样操作是引入tensorboard&#xff0c;申明一个类&#xff0c;logs是生成日志的文件夹&#xff0c;事件就在这里产生。 writer为申明的实例&#xff0c;这里做的画线操作 第一个是tags是图片的标签&#xff0c;第二个参数是y值&#xff0c;第三个是步长&#xff0c;x值 关闭…

Kotlin simple convert ArrayList CopyOnWriteArrayList MutableList

Kotlin simple convert ArrayList CopyOnWriteArrayList MutableList Kotlin读写分离CopyOnWriteArrayList_zhangphil的博客-CSDN博客Java并发多线程环境中&#xff0c;造成死锁的最简单的场景是&#xff1a;多线程中的一个线程T_A持有锁L1并且申请试图获得锁L2&#xff0c;而多…

TDengine 与煤矿智能 AI 视频管理系统实现兼容性互认

煤矿行业是一个充满危险和复杂性的领域&#xff0c;具备产业规模大、分布地域广、安全性要求高等特点&#xff0c;为了实现智能化预警、预测等目的&#xff0c;煤矿企业纷纷采用现代化的技术来提高安全性、生产效率和管理水平。煤矿智能 AI 视频管理系统可以助力企业更好地进行…

JMeter:断言之响应断言

一、断言的定义 断言用于验证取样器请求或对应的响应数据是否返回了期望的结果。可以是看成验证测试是否预期的方法。 对于接口测试来说&#xff0c;就是测试Request/Response&#xff0c;断言即可以针对Request进行&#xff0c;也可以针对Response进行。但大部分是对Respons…

基于SSM的博客系统开发

文章目录 前言1.技术选型&#xff1a;2.主要功能&#xff1a;3.项目展示&#xff1a;前台页面&#xff1a;后台页面&#xff1a; 总结 前言 提示&#xff1a;人类与强权的斗争&#xff0c;就是记忆与遗忘的斗争。 --米兰昆德拉《笑忘录》 1.技术选型&#xff1a; 开发工具&am…

android 存储新特性

分区存储 本页内容应用访问限制将分区存储与 FUSE 搭配使用 FUSE 和 SDCardFSFUSE 性能微调减轻与 FUSE 相关的性能影响隐私优势远超性能劣势MediaProvider 和 FUSE 更新 分区存储会限制应用访问外部存储空间。在 Android 11 或更高版本中&#xff0c;以 API 30 或更高版本为…

Linux Day16 多线程的一些常见问题

目录 一、多线程fork() 问题一&#xff1a;多线程中某个线程调用 fork()&#xff0c;子进程会有和父进程相同数量的线程吗&#xff1f; 1.1.1 不使用fork前&#xff0c;让线程函数和主程序打印其进程号 结果&#xff1a; 结论&#xff1a; 1.1.2 在主程序中加入fork 结果…

个人博客网站一揽子:Docker搭建图床(Lsky Pro)

Lsky Pro 介绍 Lsky Pro 是一个用于在线上传、管理图片的图床程序&#xff0c;中文名&#xff1a;兰空图床&#xff0c;你可以将它作为自己的云上相册&#xff0c;亦可以当作你的写作贴图库。 兰空图床始于 2017 年 10 月&#xff0c;最早的版本由 ThinkPHP 5 开发&#xff0…

​bing许少辉乡村振兴战略下传统村落文化旅游设计images

​bing许少辉乡村振兴战略下传统村落文化旅游设计images

JavaEE学习之--类和对象

&#x1f495;粗缯大布裹生涯&#xff0c;腹有诗书气自华&#x1f495; 作者&#xff1a;Mylvzi 文章主要内容&#xff1a;Java学习之--类和对象 类和对象 类的实例化&#xff1a; 1.什么叫做类的实例化 利用类创建一个具体的对象就叫做类的实例化&#xff01; 当我们创建了…

【消息中间件】详解mq消息积压

作者简介 目录 1.产生原因 2.解决办法 2.1.事前处理机制 2.2.事中处理机制 2.3.事后处理机制 1.产生原因 消息积压&#xff08;Message Backlog&#xff09;指的是在消息队列&#xff08;MQ&#xff09;系统中等待被处理的消息数量超过了正常的处理速度&#xff0c;导致消…

Nvm任意切换node版本号

前言&#xff1a; nvm&#xff08;Node Version Manager&#xff09;是一个用于管理Node.js版本的工具。它允许您在同一台计算机上同时安装和切换不同版本的Node.js。使用nvm&#xff0c;您可以轻松地在项目之间切换Node.js版本&#xff0c;而无需手动安装和卸载不同的版本。这…

FPGA纯verilog实现8路视频拼接显示,提供工程源码和技术支持

目录 1、前言版本更新说明免责声明 2、我已有的FPGA视频拼接叠加融合方案3、设计思路框架视频源选择OV5640摄像头配置及采集静态彩条视频拼接算法图像缓存视频输出 4、vivado工程详解5、工程移植说明vivado版本不一致处理FPGA型号不一致处理其他注意事项 6、上板调试验证并演示…

【Java 基础篇】Java 标准输出流详解:输出你的程序之美

Java 编程中&#xff0c;标准输出流是一个重要的概念。它允许我们将程序的输出信息显示在终端或控制台上&#xff0c;这对于调试、用户界面和与用户的交互非常重要。在这篇文章中&#xff0c;我们将深入探讨 Java 的标准输出流&#xff0c;了解如何使用它以及一些常见的用法和技…

libevent数据结构——TAILQ_结构体

TAILQ_结构体 TAILQ_结构体在文件event2/event_struct.h和文件event2/keyvalq_struct.h中都有定义&#xff0c;并且他们的定义都是一样的&#xff0c;定义了TAILQ_ENTRY、TAILQ_HEAD结构体&#xff1a; #ifndef TAILQ_ENTRY #define EVENT_DEFINED_TQENTRY_ #define TAILQ_EN…

JVM——10.对象的内存布局

这篇文章&#xff0c;我们来了解一下对象在内存中的布局是什么样的。 解释&#xff1a;前面有一篇文章我们讲了JVM中类的结构&#xff0c;那里讲的是一个java类&#xff0c;被编译成二进制字节码后&#xff0c;它的结构是什么样的&#xff0c;或者说按照jvm的标准&#xff0c;…