Vite+Typescript+Vue3学习笔记
Vite+Typescript+Vue3学习笔记
1、项目搭建
1.1、创建项目(yarn)
D:\WebstromProject>yarn create vite
yarn create v1.22.19
[1/4] Resolving packages...
[2/4] Fetching packages...
[3/4] Linking dependencies...
[4/4] Building fresh packages...success Installed "create-vite@4.4.1" with binaries:- create-vite- cva
√ Project name: ... vite-project
√ Select a framework: » Vue
√ Select a variant: » TypeScriptScaffolding project in D:\WebstromProject\vite-project...Done. Now run:cd vite-projectyarnyarn devDone in 14.81s.

1.2、项目配置
1、配置vue文件识别
vite默认情况下不识别.vue后缀的文件,需在vite-env.d.ts配置下
/// <reference types="vite/client" />
declare module "*.vue" {import { DefineComponent } from "vue"const component: DefineComponent<{}, {}, any>export default component
}
2、Api选择
/* Options API */
export default {props: {},data(){},computed: {},watch: {},methods: {},created(),components:{}// ...other options
}
/* Composition API */
export default {props: {},setup(),components:{}
}
Vue3推荐使用Composition API,这里关闭Vue2的Option Api
import {defineConfig} from 'vite'
import vue from '@vitejs/plugin-vue'// https://vitejs.dev/config/
export default defineConfig({define: {// 关闭Vue2 Options Api__VUE_OPTIONS_API__: false},plugins: [vue(),],
})
1.3、常用依赖
1、@types/node
ts需安装node的类型,否则使用node相关会提示找不到
# @types/node
yarn add -D @types/node
2、auto-import
用于简化Vue3中ref、reactive**、**watch和UI组件的导入
# unplugin-vue-components、unplugin-auto-import
yarn add -D unplugin-vue-components unplugin-auto-import
3、sass
# sass
yarn -D add sass
2、Composition API
2.1、响应式
可以在chrome浏览器开启自定义格式化,便于查看


1、ref
ref通常用于声明基础类型响应式数据,引用类型也可以,会隐式调用reactive,同时取值赋值都需要.value
<script setup lang="ts">
import {Ref} from "vue";
// 非响应式
// let number: number = Math.random()
// console.log(isRef(number))// 响应式
// let number = ref(Math.random())
// 显式类型约束
let number: Ref<number> = ref<number>(Math.random())
console.log(isRef(number))
const h1click = () => {// 非响应式// number = Math.random()// 响应式number.value = Math.random()console.log(number);
}
</script><template><div><h1 @click="h1click">{{ number }}</h1></div>
</template><style scoped></style>
2、shallowRef
只处理基本数据类型的响应式, 不进行对象的响应式处理(不能与ref一起用,否则会被迫更新视图)
<script setup lang="ts">
import {isShallow, Ref} from "vue";let number = shallowRef<number>(Math.random())
console.log(isShallow(number))
const h1click = () => {number.value = Math.random()console.log(number);
}
</script><template><div><h1 @click="h1click">{{ number }}</h1></div>
</template><style scoped></style>
3、reactive
reactive用于声明引用类型响应式数据,且对象解构后会失去响应式
<script setup lang="ts">let person = reactive({name: "xumeng"
})
console.log(isReactive(person))
const h1click = () => {person.name = "xumeng03"console.log(person);
}
</script><template><div><h1 @click="h1click">{{ person }}</h1></div>
</template><style scoped></style>
4、shallowReactive
只处理对象最外层属性的响应式(浅响应式),(不能与reactive一起用,否则会被迫更新视图)
<script setup lang="ts">let person = shallowReactive({name: "xumeng",hobby: ["game","code"]
})
console.log(isReactive(person))
const h1click = () => {// 浅层次数据// person.name = "xumeng03"// 深层次数据(如果浅层次&深层次数据一起变化,则会一起更新)person.hobby[0] = 'movie'console.log(person);
}
</script><template><div><h1 @click="h1click">{{ person }}</h1></div>
</template><style scoped></style>
5、toRef
将对象某个属性变为响应式
<script setup lang="ts">let person = reactive({name: "xumeng"
})
// 如果person非响应式对象,则不会引起视图更新
let name = toRef(person, 'name')
const h1click = () => {name.value = "xumeng03"console.log(person);
}
</script><template><div><h1 @click="h1click">{{ person }}</h1></div>
</template><style scoped></style>
6、toRefs
将对象的一些解构属性变为响应式
<script setup lang="ts">let person = reactive({name: "xumeng",age: 22
})
// 解构别名
let {name: pname, age: page} = toRefs(person)
const h1click = () => {pname.value = "xumeng03"page.value = 23console.log(pname, page);
}
</script><template><div><h1 @click="h1click">{{ person }}</h1></div>
</template><style scoped></style>
7、toRaw
把响应式对象变为普通对象
<script setup lang="ts">let person = reactive({name: "xumeng",age: 22
})let rperson = toRaw(person)
const h1click = () => {rperson.name = "xumeng03"rperson.age = 23console.log(rperson);
}
</script><template><div><h1 @click="h1click">{{ person }}</h1></div>
</template><style scoped></style>
2.2、修饰符
1、readonly
<script setup lang="ts">let person = reactive({name: "xumeng"
})
let rperson = readonly(person)
const h1click = () => {// 正常赋值person.name = "xumeng03"// 报错// rperson.name = "xumeng03"console.log(person);
}
</script><template><div><h1 @click="h1click">{{ person }}</h1></div>
</template><style scoped></style>
2.3、computed
1、选项式写法
参数为对象,需传入一个get和set函数自定义存取操作
<script setup lang="ts">let person = reactive({name: "xumeng03",nickName: '眼眸流转',age: 22
})
let people = computed({get() {return person.name + '-' + person.nickName},set(newValue) {[person.name, person.nickName] = newValue.split('-')}
})
const h1click = () => {people.value = '徐梦-眼眸'
}
</script><template><div><h1 @click="h1click">{{ people }}</h1></div>
</template><style scoped></style>
2、函数式写法
<script setup lang="ts">let person = reactive({name: "xumeng03",nickName: '眼眸流转',age: 22
})
let people=computed(()=>{return person.name + '-' + person.nickName
})
const h1click = () => {// 不支持修改// people.value = '徐梦-眼眸'
}
</script><template><div><h1 @click="h1click">{{ people }}</h1></div>
</template><style scoped></style>
2.4、监听
1、watch
基本类型
<script setup lang="ts">let age = ref(22)
const h1click = () => {age.value++
}
watch(age, (value, oldValue) => {console.log("监听到变化:", value, oldValue);
})
</script><template><div><h1 @click="h1click">{{ age }}</h1></div>
</template><style scoped></style>
引用类型
<script setup lang="ts">let person = reactive({name: "xumeng03",nickName: '眼眸流转',age: 22
})
let person1 = reactive({name: "xumeng03",nickName: '眼眸流转',age: 22
})
const h1click = () => {person.age++
}
let people = computed(() => {return person.name + '-' + person.nickName + '-' + person.age
})// 此时若监听person会发现新旧数据一致,可以使用computed处理一下返回(如返回新的信息或深拷贝原引用数据)
// watch(person, (value, oldValue) => {
// console.log("监听到变化:", value, oldValue);
// }, {
// // 深度监听,reactive默认就是深度监听
// deep: true,
// // 立即执行一次
// immediate: true,
// // 刷新时机
// flush: 'pre'
// })// 监听整个引用数据
watch(people, (value, oldValue) => {console.log("监听到变化:", value, oldValue);
}, {// 深度监听,reactive默认就是深度监听deep: true,// 立即执行一次immediate: true,// 刷新时机flush: 'pre'
})// 监听引用对象某个属性
watch(() => person.age, (value, oldValue) => {console.log("监听到变化:", value, oldValue);
}, {// 深度监听,reactive默认就是深度监听deep: true,// 立即执行一次immediate: true,// 刷新时机flush: 'pre'
})// 监听多个数据源
watch([person, person1], (value, oldValue) => {console.log("监听到变化:", value, oldValue);
}, {// 深度监听,reactive默认就是深度监听deep: true,// 立即执行一次immediate: true,// 刷新时机flush: 'pre'
})
</script><template><div><h1 @click="h1click">{{ people }}</h1></div>
</template><style scoped></style>
2、watchEffect
<script setup lang="ts">let age = ref(22)
const h1click = () => {age.value++
}
// watchEffect返回一个停止监听函数
const stopwatch = watchEffect((oninvalidate) => {oninvalidate(() => {console.log("变化前");})console.log(age);
})
// 停止监听
// stopwatch()
</script><template><div><h1 @click="h1click">{{ age }}</h1></div>
</template><style scoped></style>
2.5、生命周期
<script setup lang="ts">
let age = ref(22)
let h1 = ref<HTMLElement>()
// 生命周期(setup模式下无beforeCreate和created)// 挂载前
onBeforeMount(() => {console.log('挂载前', h1.value);
})
// 挂载完成
onMounted(() => {console.log('挂载完成', h1.value);
})// 更新前
onBeforeUpdate(() => {console.log('更新前', h1.value?.innerText);
})
// 更新完成
onUpdated(() => {console.log('更新完成', h1.value?.innerText);
})// 销毁前
onBeforeUnmount(() => {console.log('销毁前');
})
// 销毁后
onBeforeUnmount(() => {console.log('销毁后');
})
const h1click = () => {age.value++
}
</script><template><div><h1 @click="h1click" ref="h1">{{ age }}</h1></div>
</template><style scoped></style>
2.6、父子组件传参
1、父传子(defineProps)
父组件
<script setup lang="ts">
let PtoC1 = ref(1)
let PtoC2 = ref({name: 'xumeng03',age: 22
})
</script><template><div>我是父组件<hr><Child :PtoC1="PtoC1" :PtoC2="PtoC2"/></div>
</template><style scoped lang="scss"></style>
子组件
<script setup lang="ts">
// js形式
// const props = defineProps({
// PtoC1: {
// type: Number,
// default: '默认值'
// },
// PtoC2: {
// type: Object,
// default: {}
// }
// })// typescript类型约束
const props = defineProps<{PtoC1: number,PtoC2: {name: string,age: number}
}>()// typescript默认值
withDefaults(defineProps<{PtoC1: number,PtoC2: {name: string,age: number}
}>(), {PtoC1: 0, PtoC2: () => ({name: 'name', age: 0})
})
</script><template><div>我是子组件<br><!--来自父组件的消息1: {{ FtoC }}-->来自父组件的消息1: {{ props.PtoC1 }}<br>来自父组件的消息2: {{ props.PtoC2 }}</div>
</template><style scoped lang="scss"></style>
2、子传父(defineEmits)
父组件
<script setup lang="ts">
let Pmessage1 = ref<string>()
let Pmessage2 = reactive<{name: string,age: number
}>({name: 'name',age: 0
})
const getChildMessage1 = (message: string) => {Pmessage1.value = message
}
const getChildMessage2 = (message: {name: string,age: number
}) => {Pmessage2 = message
}
</script><template><div>我是父组件<br>来自父组件的消息1: {{ Pmessage1 }}<br>来自父组件的消息1: {{ Pmessage2 }}<hr><Child @getChildMessage1="getChildMessage1" @getChildMessage2="getChildMessage2"/></div>
</template><style scoped lang="scss"></style>
子组件
<script setup lang="ts">
let message1 = ref("xumeng03")
let message2 = reactive({name: 'xumeng03',age: 22
})
// const emit = defineEmits(['getChildMessage1', 'getChildMessage2'])
const emit = defineEmits<{(e: 'getChildMessage1', message: string): void,(e: 'getChildMessage2', message: {name: string,age: number}): void
}>()
const transValue = () => {emit('getChildMessage1', message1.value)emit('getChildMessage2', message2)
}
</script><template><div @click="transValue">我是子组件</div>
</template><style scoped lang="scss"></style>
3、父组件访问子组件
父组件
<script setup lang="ts">
import Child from "@/components/Child.vue";const child1 = ref<InstanceType<typeof Child>>()
const childAttributes = () => {console.log(child1.value.username)child1.value.changeName('xumeng03' + Math.ceil(Math.random() * 10))
}
</script><template><div @click="childAttributes">我是父组件<br>子组件属性:{{ child1 }}<hr><Child ref="child1"/></div>
</template><style scoped lang="scss"></style>
子组件
<script setup lang="ts">
let username = ref("child")
const changeName = (newName: string) => {console.log("newName:" + newName)username.value = newName
}defineExpose({username,changeName
})
</script><template><div>我是子组件</div>
</template><style scoped lang="scss"></style>
3、样式
3.1、全局样式/变量
@/style/variables.scss
$theColor: lightblue;h1 {font-size: 100px;
}
vite.config.ts
import {defineConfig} from 'vite'
import vue from '@vitejs/plugin-vue'
import path from 'path'
// 自动导入vue中ref、reactive、watch等
import AutoImport from "unplugin-auto-import/vite"
// 自动导入ui组件
import Components from 'unplugin-vue-components/vite';// https://vitejs.dev/config/
export default defineConfig({define: {// 关闭Vue2 Options Api__VUE_OPTIONS_API__: false},plugins: [vue(),AutoImport({// 在组件中不用再导入ref、reactive、watch等imports: ['vue', 'vue-router'],// 声明文件存放的位置,会自动生成,无需自己维护dts: "src/auto-import.d.ts",}),Components({// 引入组件的存放的位置,包括自定义组件dts: "src/components.d.ts",}),],resolve: {// 配置路径别名alias: {"@": path.resolve(__dirname, "./src"),},},css: {preprocessorOptions: {scss: {additionalData: `@import "@/style/variables.scss";`}}},
})
使用
<script setup lang="ts">
let age = ref(22)
const h1click = () => {age.value++
}
</script><template><div><h1 @click="h1click">年龄:{{ age }}</h1></div>
</template>
<!--注意style必须加上lang="scss"-->
<style scoped lang="scss">
h1 {color: $theColor;
}
</style>
相关文章:
Vite+Typescript+Vue3学习笔记
ViteTypescriptVue3学习笔记 1、项目搭建 1.1、创建项目(yarn) D:\WebstromProject>yarn create vite yarn create v1.22.19 [1/4] Resolving packages... [2/4] Fetching packages... [3/4] Linking dependencies... [4/4] Building fresh packages...success Installed…...
二、SQL-6.DCL-2).权限控制
*是数据库和表的通配符,出现在数据库位置上表示所有数据库,出现在表名位置上,表示所有表 %是主机名的通配符,表示所有主机。 e.g.所有数据库(*)的所有表(*)的所有权限(a…...
[OpenStack] GPU透传
GPU透传本质就是PCI设备透传,不算是什么新技术。之前按照网上方法都没啥问题,但是这次测试NVIDIA A100遇到坑了。 首先是禁用nouveau 把intel_iommuon rdblacklistnouveau写入/etc/default/grub的cmdline,然后grub2-mkconfig -o /etc/grub2.c…...
无涯教程-jQuery - Progressbar组件函数
小部件进度条功能可与JqueryUI中的小部件一起使用。一个简单的进度条显示有关进度的信息。一个简单的进度条如下所示。 Progressbar - 语法 $( "#progressbar" ).progressbar({value: 37 }); Progressbar - 示例 以下是显示进度条用法的简单示例- <!doctype …...
[SQL挖掘机] - 窗口函数 - rank
介绍: rank() 是一种常用的窗口函数,它为结果集中的每一行分配一个排名(rank)。这个排名基于指定的排序顺序,并且在遇到相同的值时,会跳过相同的排名。 用法: rank() 函数的语法如下: rank() over ([pa…...
VBAC多层防火墙技术的研究-状态检测
黑客技术的提升和黑客工具的泛滥,造成大量的企业、机构和个人的电脑系统遭受程度不同的入侵和攻击,或面临随时被攻击的危险。迫使大家不得不加强对自身电脑网络系统的安全防护,根据系统管理者设定的安全规则把守企业网络,提供强大的、应用选通、信息过滤、流量控制、网络侦…...
PHP8的数据类型-PHP8知识详解
在PHP8中,变量不需要事先声明,赋值即声明。 不同的数据类型其实就是所储存数据的不同种类。在PHP8.0、8.1中都有所增加。以下是PHP8的15种数据类型: 1、字符串(String):用于存储文本数据,可以使…...
明晚直播:可重构计算芯片的AI创新应用分享!
大模型技术的不断升级及应用落地,正在推动人工智能技术发展进入新的阶段,而智能化快速增长和发展的市场对芯片提出了更高的要求:高算力、高性能、灵活性、安全性。可重构计算区别于传统CPU、GPU,以指令驱动的串行执行方式…...
flask 点赞系统
dianzan.html页面 <!DOCTYPE html> <html lang"en"> <head><meta charset"UTF-8"><title>点赞系统</title> </head> <body><h2>这是一个点赞系统</h2><table border"1"><…...
关于Java的多线程实现
多线程介绍 进程:进程指正在运行的程序。确切的来说,当一个程序进入内存运行,即变成一个进程,进程是处于运行过程中的程序,并且具有一定独立功能。 线程:线程是进程中的一个执行单元,负责当前进…...
如何判断某个视频是深度伪造的?
目录 一、前言 二、仔细检查面部动作 三、声音可以提供线索 四、观察视频中人物的身体姿势 五、小心无意义的词语 深造伪造危险吗? 一、前言 制作深度伪造视频就像在Word文档中编辑文本一样简单。换句话说,您可以拍下任何人的视频,让他…...
ESP32(MicroPython) 四足机器人(一)
最近决定研究一下四足机器人,但市面上的产品,要么性价比低,要么性能达不到要求。本人就另外买了零件,安装到之前的一个麦克纳姆轮底盘的底板上。(轮子作为装饰,使用铜柱固定) 舵机使用MG996R&a…...
力扣刷题记录---利用python实现链表的基本操作
文章目录 前言一、利用python实现链表的基本操作1.节点的定义使用类实现:1.链表的定义使用类实现:3.判断是否为空函数实现:4.链表长度函数实现:5.遍历链表函数实现:6.头插法函数实现:7.尾插法函数实现&…...
OpenAI重磅官宣ChatGPT安卓版本周发布,现已开启下载预约,附详细预约教程
7月22号,OpenAI 突然宣布,安卓版 ChatGPT 将在下周发布!换句话说,本周安卓版 ChatGPT正式上线! 最早,ChatGPT仅有网页版。 今年5月,iOS版ChatGPT正式发布,当时OpenAI表示Android版将…...
PHP 支付宝支付、订阅支付(周期扣款)整理汇总
最近项目中需要使用支付宝的周期扣款,整理一下各种封装方法 APP支付(服务端) /******************************************************* 调用方法******************************************************/function test_pay(){$isSubscri…...
python-pytorch基础之神经网络回归
这里写目录标题 定义数据集定义函数生成数据集 使用Dataloader加载dataset定义神经网络定义实例化查看是否是输出的一个 训练编写trian方法训练并保存模型 测试模型结果构造数据测试结论 定义数据集 import torch import random定义函数 # 生成数据 def get_rancledata():wid…...
linux中通过.desktop文件执行bash命令打开chrome浏览器并传参
.desktop 文件介绍 Ecex 参数介绍 Code 描述 %f %f指向临时文件。用于不了解URL语法的程序。 %F 文件列表。用于可以一次打开多个本地文件的应用程序。每个文件作为单独的参数传递给可执行程序。 %u 单一的URL或者本地文件 %U %u的复数 %i 如果Icon 为空,不应该填写此参数。…...
ChatGPT的应用与发展趋势:解析人工智能的新风口
目录 优势 应用领域 发展趋势 总结 在人工智能技术迅猛发展的时代,自然语言处理系统的提升一直是研究者们追求的目标。作为人工智能领域的重要突破之一,ChatGPT以其出色的语言模型和交互能力,在智能对话领域取得了重要的进展。 ChatGPT是…...
使用maven打jar包时,如何只把依赖的其它jar中的类打进jar包,没有依赖的其它jar包的类文件不打进来?
简介 使用Maven打包时,默认情况下,所有依赖的jar包都会被打包到生成的jar文件中。 如果只想将依赖的其他jar中的类文件打进来,而不包含其它jar包,可以使用Maven的 maven-shade-plugin插件进行配置。 步骤 以下是一个示例配置&…...
arm neon/fpu/mfloat
neon官网介绍: Arm Neon technology is an advanced Single Instruction Multiple Data (SIMD) architecture extension for the A-profile and R-profile processors. Neon technology is a packed SIMD architecture. Neon registers are considered as vectors of elements …...
Photon光影包:颠覆级Minecraft视觉体验的沉浸式渲染方案
Photon光影包:颠覆级Minecraft视觉体验的沉浸式渲染方案 【免费下载链接】photon A gameplay-focused shader pack for Minecraft 项目地址: https://gitcode.com/gh_mirrors/photon3/photon 在像素化的方块世界中,如何突破视觉边界实现电影级画面…...
3步打造游戏性能优化神器:DLSS Swapper零基础掌握指南
3步打造游戏性能优化神器:DLSS Swapper零基础掌握指南 【免费下载链接】dlss-swapper 项目地址: https://gitcode.com/GitHub_Trending/dl/dlss-swapper DLSS Swapper是一款专为PC游戏玩家设计的DLSS版本管理工具,通过自动化版本切换、智能游戏扫…...
汇川PLC与IS620N伺服驱动实战:手把手教你完成EtherCAT网络配置与电机命名
汇川PLC与IS620N伺服驱动深度配置指南:从EtherCAT组态到电机精准控制 在工业自动化领域,伺服系统的稳定性和响应速度直接决定了设备性能的上限。汇川AM600系列PLC搭配IS620N伺服驱动组成的EtherCAT网络,正成为越来越多自动化工程师的首选方案…...
从腾讯AI架构师那里听到的:他们正在重点研究的4个新前沿AI方向
腾讯AI架构师揭秘:当下重点突破的4个前沿AI方向 清晨的深圳滨海大厦会议室里,腾讯AI Lab的架构师张明(化名)放下咖啡杯,翻开电脑里的项目进度表——屏幕上跳动的图表里,“MoE轻量化” “多模态因果推理” “…...
【花雕学编程】代码泄露之后:深度剖析Claude开源对开发者生态的冲击与机遇
导语:2026年3月31日,Anthropic 旗下 Claude Code CLI 客户端源码意外泄露,1906个源文件、51.2万行TypeScript代码被开发者备份至 GitHub 仓库 instructkr/claude-code,标注为“仅供研究”。这场看似偶然的打包失误,并非…...
从单核到16核:用程序员思维图解CPU参数(附性能测试代码)
从单核到16核:用程序员思维图解CPU参数(附性能测试代码) 在开发高性能应用时,CPU的选择往往直接决定了程序的执行效率。但面对琳琅满目的参数——主频、核心数、线程数、缓存大小、架构代际——开发者该如何做出明智决策ÿ…...
5分钟上手MouseClick:让重复点击自动化的3个核心技巧
5分钟上手MouseClick:让重复点击自动化的3个核心技巧 【免费下载链接】MouseClick 🖱️ MouseClick 🖱️ 是一款功能强大的鼠标连点器和管理工具,采用 QT Widget 开发 ,具备跨平台兼容性 。软件界面美观 ,操…...
马上深挖!!!三段逆置如何实现数组轮转?!用最简单的话让你秒懂
一、目的给定一个数组和一个整数k,让数组向右轮转k个数。如令[1,2,3,4,5,6]向右轮转3个数,结果为[4,5,6,1,2,3]。二、代码#include <iostream> using namespace std;void swap(int* a,int* b) {int tmp*a;*a*b;*btmp;return; }void reverse(int* a…...
硬件工程师必看:从PCIe到车载以太网,手把手教你搞定SerDes信号完整性设计(附仿真避坑指南)
硬件工程师实战指南:SerDes信号完整性设计的黄金法则与仿真避坑 在当今高速数字电路设计中,SerDes技术已经成为连接芯片与系统的关键桥梁。无论是数据中心服务器中的PCIe 5.0接口,还是智能驾驶系统中的车载以太网,信号完整性问题都…...
亚马逊Buy for Me代购服务全流程实测:从下单到收货的完整避坑手册
亚马逊Buy for Me代购服务实战解析:从入门到精通的完整指南 跨境购物早已不是新鲜事,但每次看到海外电商平台上那些国内买不到的好物,心里总免不了痒痒的。亚马逊最新推出的Buy for Me服务,或许正是解决这一痛点的钥匙。作为一名长…...
