vue3与ts的组合式API

vue3与ts的组合式API

props

1.基本props
<script setup lang="ts">
const props = defineProps<{foo: stringbar?: number
}>()
</script>
2.抽离props
<script setup lang="ts">
interface Props {foo: stringbar?: number
}const props = defineProps<Props>()
</script>
3.抽离和导入type
<script setup lang="ts">
import type { Props } from './foo'const props = defineProps<Props>()
</script>
4.默认值props
export interface Props {msg?: stringlabels?: string[]
}const props = withDefaults(defineProps<Props>(), {msg: 'hello',labels: () => ['one', 'two']
})
5.复杂props
<script setup lang="ts">
interface Book {title: stringauthor: stringyear: number
}const props = defineProps<{book: Book
}>()
</script>

emits

一个类型字面量,其中键是事件名称,值是数组或元组类型,表示事件的附加接受参数。示例使用了具名元组,因此每个参数都可以有一个显式的名称。

<script setup lang="ts">
// 基于类型
const emit = defineEmits<{(e: 'change', id: number): void(e: 'update', value: string): void
}>()// 3.3+: 可选的、更简洁的语法
const emit = defineEmits<{change: [id: number]update: [value: string]
}>()
</script>

ref()

1.自动推导
import { ref } from 'vue'// 推导出的类型:Ref<number>
const year = ref(2020)// => TS Error: Type 'string' is not assignable to type 'number'.
year.value = '2020'
2.复杂ref
import { ref } from 'vue'
import type { Ref } from 'vue'const year: Ref<string | number> = ref('2020')year.value = 2020 // 成功!

个人建议使用第二种,字少了,且无需导入import type { Ref } from 'vue'

// 得到的类型:Ref<string | number>
const year = ref<string | number>('2020')year.value = 2020 // 成功!

注意:如果你指定了一个泛型参数但没有给出初始值,那么最后得到的就将是一个包含 undefined 的联合类型:

// 推导得到的类型:Ref<number | undefined>
const n = ref<number>()

recative()

1.自动推导
import { reactive } from 'vue'// 推导得到的类型:{ title: string }
const book = reactive({ title: 'Vue 3 指引' })
2.复杂reactive
import { reactive } from 'vue'interface Book {title: stringyear?: number
}const book: Book = reactive({ title: 'Vue 3 指引' })

注意:不推荐使用 reactive()泛型参数,因为处理了深层次 ref 解包的返回值与泛型参数的类型不同。

错误示例:

import { reactive } from 'vue'interface Book {title: string;year?: number;
}// 不推荐:使用了泛型参数,但返回的类型与Book不同
const book: Book = reactive<Book>({ title: 'Vue 3 指引' });

正确示例,使用toRefs()

import { reactive, toRefs } from 'vue'interface Book {title: string;year?: number;
}// 创建一个响应式的Book对象
const bookReactive = reactive({ title: 'Vue 3 指引' });// 使用toRefs()将每个属性转换为Ref,确保类型安全
const bookRefs = toRefs(bookReactive);// 现在bookRefs是一个Record类型,其中的属性具有与Book相同的类型
const book: { title: Ref<string>; year?: Ref<number | undefined> } = bookRefs;// 或者,如果你知道你只会在模板中使用,可以使用类型断言
const bookWithAssertion = {title: bookRefs.title as Ref<string>,year: bookRefs.year as Ref<number | undefined>,
} as const;

computed()

1.自动推导
import { ref, computed } from 'vue'const count = ref(0)// 推导得到的类型:ComputedRef<number>
const double = computed(() => count.value * 2)// => TS Error: Property 'split' does not exist on type 'number'
const result = double.value.split('')
2.显式指定
const double = computed<number>(() => {// 若返回值不是 number 类型则会报错
})

为事件处理函数标注类型

**在处理原生 DOM 事件时,应该为我们传递给事件处理函数的参数正确地标注类型。**让我们看一下这个例子:

<script setup lang="ts">
function handleChange(event) {// `event` 隐式地标注为 `any` 类型console.log(event.target.value)
}
</script><template><input type="text" @change="handleChange" />
</template>

没有类型标注时,这个 event 参数会隐式地标注为 any 类型。这也会在 tsconfig.json 中配置了 "strict": true"noImplicitAny": true 时报出一个 TS 错误。因此,建议显式地为事件处理函数的参数标注类型。此外,你在访问 event 上的属性时可能需要使用类型断言:

function handleChange(event: Event) {console.log((event.target as HTMLInputElement).value)
}

为 provide / inject 标注类型

const foo = inject<string>('foo') // 类型:string | undefined ???

为模板引用标注类型

模板引用需要通过一个显式指定的泛型参数和一个初始值 null 来创建:

<script setup lang="ts">
import { ref, onMounted } from 'vue'const el = ref<HTMLInputElement | null>(null)onMounted(() => {el.value?.focus()
})
</script><template><input ref="el" />
</template>

可以通过类似于 MDN 的页面来获取正确的 DOM 接口。https://developer.mozilla.org/zh-CN/docs/Web/API/HTMLInputElement

注意为了严格的类型安全,有必要在访问 el.value 时使用可选链或类型守卫。这是因为直到组件被挂载前,这个 ref 的值都是初始的 null,并且在由于 v-if 的行为将引用的元素卸载时也可以被设置为 null

为组件模板引用标注类型

有时,你可能需要为一个子组件添加一个模板引用,以便调用它公开的方法。举例来说,我们有一个 MyModal 子组件,它有一个打开模态框的方法:

<!-- MyModal.vue -->
<script setup lang="ts">
import { ref } from 'vue'const isContentShown = ref(false)
const open = () => (isContentShown.value = true)defineExpose({open
})
</script>

为了获取 MyModal 的类型,我们首先需要通过 typeof 得到其类型,再使用 TypeScript 内置的 InstanceType 工具类型来获取其实例类型:

<!-- App.vue -->
<script setup lang="ts">
import MyModal from './MyModal.vue'const modal = ref<InstanceType<typeof MyModal> | null>(null)const openModal = () => {modal.value?.open()
}
</script>

如果组件的具体类型无法获得,或者你并不关心组件的具体类型,那么可以使用 ComponentPublicInstance。这只会包含所有组件都共享的属性,比如 $el

import { ref } from 'vue'
import type { ComponentPublicInstance } from 'vue'const child = ref<ComponentPublicInstance | null>(null)

官网链接

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

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

相关文章

leetcode146.LRU缓存,从算法题引入,全面学习LRU和链表哈希表知识

leetcode146. LRU 缓存 题目链接 请你设计并实现一个满足 LRU (最近最少使用) 缓存约束的数据结构。 实现 LRUCache 类&#xff1a; LRUCache(int capacity) 以 正整数 作为容量 capacity 初始化 LRU 缓存 int get(int key) 如果关键字 key 存在于缓存中&#xff0c;则返回关…

【QT】父子按钮同时响应点击事件

QPushButton如何响应点击事件 QPushButton::event(QEvent *e) 。可以看到在QPushButton中的event函数中并没有鼠标点击相关的操作&#xff0c;那么我们去QAbstractButton::event中寻找 damn it!。依然没有那我们去QWidget::event中寻找 damn it! 只有mousePressEvent mouseR…

leetcode165.比较版本号,简单模拟

leetcode165.比较版本号 给你两个 版本号字符串 version1 和 version2 &#xff0c;请你比较它们。版本号由被点 ‘.’ 分开的修订号组成。修订号的值 是它 转换为整数 并忽略前导零。 比较版本号时&#xff0c;请按 从左到右的顺序 依次比较它们的修订号。如果其中一个版本字…

主流摄像机:海康、大华、宇视、华为等RTSP格式

主流摄像机&#xff1a;海康、大华、宇视、华为等RTSP格式 解决方案速览海康摄像机大华摄像机宇视摄像机华为摄像机 解决方案速览 品牌rtsp格式rtsp举例海康rtsp://[username]:[password][ip]:[port]/[codec]/[channel]/[subtype]/av_streamrtsp://admin:admin123192.168.1.10…

libcef.dll丢失的解决方法-多种libcef.dll亲测有效解决方法分享

libcef.dll是Chromium Embedded Framework (CEF)的核心动态链接库&#xff0c;它为开发者提供了一个将Chromium浏览器嵌入到本地桌面应用程序中的解决方案。这个库使得开发者能够利用Chromium的强大功能&#xff0c;如HTML5、CSS3、JavaScript等&#xff0c;来创建跨平台的应用…

罕见!史诗级“大堵船”

新加坡港口的停泊延误时间已延长至7天&#xff0c;积压的集装箱数量达到惊人的450000标准箱&#xff0c;远超新冠疫情暴发时期的数轮高点。业内认为&#xff0c;近期东南亚恶劣的天气情况加剧了该区域港口拥堵。 5月31日&#xff0c;上海航运交易所&#xff08;下称“航交所”…

重生奇迹MU召唤师如何学习狂暴术?

一、了解狂暴术的基本信息 狂暴术是一种非常强大的技能&#xff0c;可以让召唤师的攻击力和防御力大幅度提高&#xff0c;但同时也会增加自身的伤害。在使用狂暴术之前&#xff0c;召唤师需要仔细考虑自己的状态和对手的情况。 二、学习狂暴术的方法 1.通过任务学习 在游戏…

Docker安装与使用 --学习笔记

一、概述 Docker是什么? Docker是一种工具&#xff0c;类似于一个虚拟箱子&#xff0c;可以把软件和它运行所需要的环境打包放进这个箱子里。这样&#xff0c;无论这个箱子放到哪里&#xff0c;软件都能像在原来的地方一样运行&#xff0c;不会因为换了地方就出问题。 假设…

uniapp使用数据持久化存储

什么是持久化存储 持久化存储是指将数据存储在非易失性介质中&#xff0c;以保证数据在系统重启或断电后仍能保持不变。这种存储方式确保数据持久存储并且可靠地被读取和访问&#xff0c; 简答来说&#xff1a;就是防止丢失&#xff0c;长期存储 为什么要用持久化存储 Pini…

leetcode5 最长回文子串

给你一个字符串 s&#xff0c;找到 s 中最长的 回文 子串。 示例 1&#xff1a; 输入&#xff1a;s "babad" 输出&#xff1a;"bab" 解释&#xff1a;"aba" 同样是符合题意的答案。示例 2&#xff1a; 输入&#xff1a;s "cbbd" 输…

【Java】一文看懂Thread 线程池的 7 种创建方式、任务队列及自定义线程池(代码示例)

本文摘要&#xff1a;【Java】Thread 线程池的 7 种创建方式及自定义线程池&#xff08;代码示例版&#xff09; &#x1f60e; 作者介绍&#xff1a;我是程序员洲洲&#xff0c;一个热爱写作的非著名程序员。CSDN全栈优质领域创作者、华为云博客社区云享专家、阿里云博客社区专…

编写一款2D CAD/CAM软件(十九)点选图形

点选图元原理 设定鼠标敏感范围,比如选中鼠标点击位置5个像素内距离最近的图元;当鼠标点击时,求解点击位置在几何坐标系下坐标点与附近几何图元的距离;如果到图元距离小于设定的鼠标敏感范围,则视为图形可选中;进一步,如果多个图元满足被选中的条件,则只选中距离最近的…

彩灯控制器设计 74ls160+ne555实现

一、选题背景 数字电子技术在我们生活中的应用非常之广泛,不论是在各个方面都会涉及到它,小到家用电器的自动控制,大到神舟九号和天空一号航天器的设计,都无可避免的要运用它。并且鉴于以理论推动实践及理论实践相结合为指导思想,特此用我们所学的理论知识来实践这次课程设…

低空经济国外经验及发展重点

国外先进经验 1.精准分类管理 美国将空域划分五大类&#xff0c;主要包括A类&#xff08;高空管制空域&#xff09;、B类&#xff08;繁忙终端管制空域&#xff09;、C类&#xff08;一般终端管制空域&#xff09;、D类&#xff08;机场管制空域&#xff09;和E类&#xff08…

UVa12273/LA4958 Palindromic DNA

UVa12273/LA4958 Palindromic DNA 题目链接题意分析AC 代码 题目链接 本题是2010年icpc欧洲区域赛西南欧赛区的的E题 题意 DNA由四种核苷碱基A、G、T、C组成&#xff0c;它们形成环状排序。当今能对DNA进行修改&#xff08;但不能同时对相邻位置进行修改&#xff09;&#xff…

【云原生】Docker Compose 使用详解

目录 一、前言 二、Docker Compose 介绍 2.1 Docker Compose概述 2.2 Docker Compose特点 2.3 Docker Compose使用场景 三、Docker Compose 搭建 3.1 安装docker环境 3.2 Docker Compose安装方式一 3.2.1 下载最新版/如果不是最新可替换最新版本 3.2.2 设置权限 3.2.…

Q-Learning 简介:初学者教程(1)

一、说明 强化学习强调无模型学习算法&#xff0c;因此出现Q-Learning&#xff0c;Q-Learning算法酷似“有限状态自动机”模型&#xff0c;只是增加了奖励机制和Agent机制&#xff0c;而Agent与粒子群算法、蒙特卡洛算法是有关的。本文介绍这个算法框架。 &#xff0c; 二、QL框…

项目管理之maven svn

管理jar包之间依赖关系 编译、打包、清理、测试等一系列构建工具 一、Maven的标志 1、每一个maven工程都有一个pom.xml maven项目坐标 <groupId>com.aaa</groupId>//项目路径 <artifactId>web</artifactId>项目名称 <version>0.0.1-SNAPS…

C语言—深入理解指针(5)

1. sizeof 和 strlen 的对比 1.1 sizeof 在学习操作符的时候&#xff0c;我们学习了 sizeof&#xff0c;sizeof 是计算变量所占内存空间大小的&#xff0c;单位是字节&#xff0c;如果操作数是类型的话&#xff0c;计算的是使用类型创建的变量所占内存空间的大小。 sizeof 只…

西瓜播放器xgplayer设置自动播放踩坑

上图是官网&#xff08;西瓜视频播放器官方中文文档&#xff09;的介绍&#xff0c;相信大家都是按照官网配置去做的&#xff0c;但是并没有什么用&#xff0c;插件很好用&#xff0c;但是属性不全&#xff0c;真的很悔恨&#xff0c;找遍 api 都没有找到自动播放的属性&#x…