vue3基础学习总结
01-gitting-started
vue3基础
<template>
<div>
{{ count }}
<button @click="handelClick">add</button>
</div>
</template>
<script setup>
import { ref } from 'vue';
const count = ref(0)
const handelClick = () => {
count.value ++
}
</script>
<style lang="css">
</style>
02-template-syntax
模版语法
<template>
<div>
{{ rawHtml }}
</div>
<div v-html="rawHtml"></div>
<div v-bind="obj">obj</div>
<button @click="handelClick">反转切换</button>
<div v-if="toggle">是</div>
<div v-else>否</div>
<div v-bind:title="title">我有标题</div>
<div>
{{ title2.split('').reverse().join('') }}
</div>
<div>
<p>{{ inputVal }}</p>
<!-- <input type="text" v-on:keyup.enter="hanedlKeyup" /> -->
<input type="text" v-on:keyup="hanedlKeyup" />
</div>
</template>
<script setup>
import { ref } from 'vue';
const rawHtml = ref('<p>2022</p>')
const title = '我是标题'
const title2 = 'hello vue3'
const obj = ref({
id: '01',
class: 'box'
})
const toggle = ref(true)
const handelClick = () => {
toggle.value = !toggle.value
}
const inputVal = ref('')
const hanedlKeyup = (e)=>{
console.log(e.target.value)
inputVal.value = e.target.value
}
</script>
<style lang="css">
</style>
03-reactivity-fundament
响应式基础
<template>
<div>
<button @click="handelClickRef">ref add {{count}}</button>
<button @click="handelClickRec">reactive add {{state.count}}</button>
</div>
</template>
<script setup>
import { ref, reactive } from 'vue';
const count = ref(0)
const state = reactive({
count: 0
})
const handelClickRef = ()=>{
count.value++
}
const handelClickRec = ()=>{
state.count++
}
</script>
<style lang="css">
</style>
04-computed-properties
<template>
<div>
<p>{{count}}</p>
{{doubleCount}}
<!-- {{doubleCount()}} -->
</div>
<div>
<button @click="handelClick">add</button>
</div>
</template>
<script setup>
import { ref, computed } from 'vue'
const count = ref(1)
const handelClick = ()=>{
count.value++
}
const doubleCount = computed(()=>{
return count.value *2
})
// const doubleCount = ()=>{
// return count.value *2
// }
</script>
<style lang="css">
</style>
05-class-style
动态样式
<template>
<div :class="[italic,{a:isA,b:isB}]" class="c d">
<p>hello vue3</p>
</div>
<div>
<button @click="handelClick">change</button>
</div>
<div><example></example></div>
</template>
<script setup>
import { ref } from 'vue';
import example from './Example.vue'
const italic = ref('italic')
const isA = ref(true)
const isB = ref(true)
const handelClick = () => {
isA.value = !isA.value
}
</script>
<style lang="css">
.a{
color: red;
}
.b{
font-size: 50px;
}
.c{
font-weight: 900;
}
.d{
text-decoration: underline;
}
.italic{
font-style: italic;
}
</style>
<template>
<ul class="box">
<li v-for="item, index in list"
:class="{active:index === crunteIndex}"
@click="handelClick(index)"
>
{{item}}
</li>
</ul>
</template>
<script setup>
import { ref } from 'vue';
const list = ref(['line 1', 'line 2', 'line 3'])
const crunteIndex =ref(0)
const handelClick = (index) => {
crunteIndex.value = index
}
</script>
<style lang="css">
.box{
border: 1px solid #999;
padding: 20px;
}
.box li{
cursor: pointer;
}
.active{
color: red;
font-size: 30px;
}
</style>
06-condition-rendering
条件渲染
<template>
<div v-if="isShow >= 75">{{isShow}}</div>
<div>
{{ count }}
<button @click="handelClick">tagger</button>
</div>
</template>
<script setup>
import { ref } from 'vue';
const isShow = ref(65)
const handelClick = () => {
isShow.value = 85
}
</script>
<style lang="css">
</style>
07-list-rendering
遍历渲染
<template>
<div>
<ul>
<template v-for="item,index in bookList">
<li v-if="item.type !== '历史'">{{index+1}}: {{item.name}} --- {{item.user}}</li>
</template>
</ul>
</div>
<div>
<ul>
<li v-for="n,u,i in course">{{i}} - {{u}}: {{n}}</li>
</ul>
</div>
</template>
<script setup>
import { ref, reactive } from 'vue';
const course = reactive({
name: '轮语',
user: '孔子',
time: '春秋战国'
})
const bookList = ref([
{
id:'01',
name:'红楼梦',
user:'罗惯中',
type: '四大名著'
},
{
id:'02',
name:'西游记',
user:'吴承恩',
type: '四大名著'
},
{
id:'03',
name:'三国演义',
user:'罗惯中',
type: '四大名著'
},
{
id:'04',
name:'水浒传',
user:'罗惯中',
type: '四大名著'
},
{
id:'03',
name:'史记',
user:'司马迁',
type: '历史'
}
])
</script>
<style lang="css">
</style>
08-event
事件处理
<template>
<div>
<p>{{ count }}</p>
<p>{{numb}}</p>
<p>{{ text }}</p>
<button @click="handel1(), handel2()">add</button>
<input type="text" @input="handelInput(100, $event)" />
</div>
</template>
<script setup>
import { ref } from 'vue';
const count = ref('事件处理')
const numb = ref(0)
const text =ref('')
const handelInput = (num, e) => {
numb.value += num
text.value = e.target.value
}
//一个动作触发2个事件,vue3特有新属性
const handel1 = ()=>{
console.log('事件1')
}
const handel2 = ()=>{
console.log('事件2')
}
</script>
<style lang="css">
</style>
09-form
表单
<template>
<div>
{{name}}
<input type="text" v-model="name" />
</div>
<div>
<textarea v-model="about"></textarea>
</div>
<div>
隐藏:<input type="checkbox" v-model="isShow" />{{isShow ? '是' : '否'}}
</div>
<div>
{{sex}}
<input type="radio" value="男" v-model="sex" />男
<input type="radio" value="女" v-model="sex" />女
<input type="radio" value="保密" v-model="sex" />保密
</div>
<div>
{{interest}}
<input type="checkbox" value="教育" v-model="interest" />教育
<input type="checkbox" value="动漫" v-model="interest" />动漫
<input type="checkbox" value="新闻" v-model="interest" />新闻
</div>
<div>
{{city}}
<select v-model="city">
<option>北京</option>
<option>上海</option>
<option>广州</option>
</select>
</div>
<div>
{{time}}
<select v-model="time" @click="handelClick" multiple>
<option>06:00</option>
<option>08:00</option>
<option>10:00</option>
<option>12:00</option>
<option>14:00</option>
</select>
</div>
</template>
<script setup>
import { ref } from 'vue';
const name = ref('')
const about =ref('')
const isShow = ref(true)
const sex = ref('')
const interest = ref([])
const city = ref('广州')
const time = ref([])
const handelClick =(e)=>{
console.log(e.target.value)
}
</script>
<style lang="css">
div{
margin-bottom: 10px;
}
</style>
10-life-cycle
生命周期
<template>
<div>
<p id="box">{{ count }}</p>
</div>
</template>
<script setup>
//生命周期
import { ref, onMounted, onBeforeMount, onBeforeUpdate, onUpdated, onBeforeUnmount, onUnmounted } from 'vue';
const count = ref(0)
let t = null
onMounted(()=>{
//加载后
console.log('加载后----->',document.getElementById('box').innerHTML)
t = setTimeout(()=>{
count.value = 1000
},1000)
})
onBeforeMount(()=>{
//加载前
// console.log('加载前----->',document.getElementById('box').innerHTML)
count.value = 100
})
onBeforeUpdate(()=>{
//数据更新前,DOM不变
console.log('更新前DOM----->',document.getElementById('box').innerHTML)
console.log('更新前value----->',count.value)
})
onUpdated(()=>{
//更新后
console.log('更新后----->',document.getElementById('box').innerHTML)
})
onBeforeUnmount(()=>{
//销毁前
// console.log('销毁前----->',document.getElementById('box').innerHTML)
})
onUnmounted(()=>{
//销毁后
// console.log('销毁后----->',document.getElementById('box').innerHTML)
clearTimeout(t)
})
</script>
<style lang="css">
</style>
11-watcher
侦听器
<template>
<div>
{{ count }}
<p>{{doubleCount}}</p>
<p>{{text}}</p>
<button @click="handelClick">add</button>
</div>
</template>
<script setup>
//侦听器
import { computed } from '@vue/reactivity';
import { ref, watchEffect, watch } from 'vue';
const count = ref(1)
const doubleCount = computed(()=>count.value*2)
const text = ref('hello')
const handelClick = () => {
count.value ++
}
watchEffect(()=>{
//侦听所有条件的变化,页面加载时会执行一次
console.log('count变化为:'+count.value)
})
watch(
//精确侦听具体某一条件的变化,页面加载时不触发
// count,
// ()=>{
// console.log('----')
// }
()=>{
text.value = 'vue3'
//可在条件发生变化前执行某些逻辑
return count.value//侦听的条件
},
()=>{
console.log('count发生变化了')
//侦听到变化后执行逻辑
}
)
</script>
<style lang="css">
</style>
12-components
全局组件与局部组件
import { createApp } from 'vue'
import App from './App.vue'
import GlobalComponents from './views/12-components/GlobalComponents.vue'
const app = createApp(App)
app.component('GC',GlobalComponents)
app.mount('#app')
<template>
<div>
<GC></GC>
</div>
<div>
<Child></Child>
</div>
</template>
<script setup>
//注册组件
import Child from './Child.vue'
</script>
<style lang="css">
</style>
<template>
<div>
Child
</div>
</template>
<script setup>
//局部注册组件
</script>
<style lang="css">
</style>
<template>
<div>
Global
</div>
</template>
<script setup>
//全局注册组件
</script>
<style lang="css">
</style>
13-props
父子传参事件(父传子)
<template>
<div>
<Child2 :count="count" @my-event2="handelEvent"></Child2>
</div>
<div>
<Child1 :count="count" @my-event1="handelClick"></Child1>
</div>
<div>
{{title}}
</div>
</template>
<script setup>
//注册组件
import {ref} from 'vue'
import Child1 from './Child1.vue'
import Child2 from './Child2.vue'
const title = ref('')
const count = ref(100)
const handelClick =(e)=>{
console.log('来自child1-->', e.value)
title.value += e.value
}
const handelEvent=(e)=>{
console.log('来自child2-->', e.value)
title.value += e.value
}
</script>
<style lang="css">
</style>
<template>
<div>
Child1
<p>{{count}}</p>
</div>
</template>
<script setup>
//局部注册组件
import {ref, onMounted} from 'vue'
const props = defineProps(['count'])
const title = ref('hello')
const emit = defineEmits(['my-event1'])
console.log('child1--->', props.count)
onMounted(()=>{
emit('my-event1', title)
})
</script>
<style lang="css">
</style>
<template>
<div>
Child2
</div>
</template>
<script setup>
//局部注册组件
import {ref, onMounted} from 'vue'
const title = ref ('vue3')
const emit = defineEmits(['my-event2'])
onMounted(()=>{
emit('my-event2', title)
})
</script>
<style lang="css">
</style>
14-components-event
父子传参事件(子传父)
<template>
<div>
{{title}}
<Child v-model:titleEvent="title"></Child>
</div>
</template>
<script setup>
//注册组件
import {ref} from 'vue'
import Child from './Child.vue'
const title = ref('hello')
</script>
<style lang="css">
</style>
<template>
<div>
Child
</div>
</template>
<script setup>
//局部注册组件
import {ref, onMounted} from 'vue'
const props = defineProps(['titleEvent'])
const emit =defineEmits(['update:titleEvent'])
const title = ref('World')
onMounted(()=>{
console.log('props--->', props.titleEvent)
let obj = props.titleEvent
emit('update:titleEvent', obj += title.value)
})
</script>
<style lang="css">
</style>
15-fallthrough-attrs
组件透传
<template>
<div>
<Child title="hello" class="world"></Child>
</div>
</template>
<script setup>
import { ref } from 'vue';
import Child from './Child.vue'
</script>
<style lang="css">
</style>
<template>
<div id="child">
Child
</div>
</template>
<script>
export default {
inheritAttrs: false //阻止组件之间的透传
}
</script>
<script setup>
//局部注册组件
import {ref, useAttrs} from 'vue'
const attrs = useAttrs()
console.log('class-->', attrs) //通过useAttrs透传可以直接获取父组件继承过来的所有属性
</script>
<style lang="css">
.world{
font-size: 50px;
color: red;
}
</style>
16-slots
插槽
<template>
<div>
<Child>
<!-- <template #default="data"> -->
<template v-slot:default="data">
<div>{{str}} {{data.mark2}} world {{data.mark}}</div>
</template>
<template v-slot:line2>
<div>{{str}} slot</div>
</template>
</Child>
</div>
</template>
<script setup>
import { ref } from 'vue';
import Child from './Child.vue'
const str = ref('hello')
</script>
<style lang="css">
</style>
<template>
<div>
<slot :mark="mark" mark2="--->"></slot>
<slot name="line2"></slot>
</div>
</template>
<script setup>
//局部注册组件
import {ref} from 'vue'
const mark = ref('!!!')
</script>
<style lang="css">
</style>
17-inject-provide
依赖注入
<template>
<div>
<Child1></Child1>
<Child2></Child2>
</div>
</template>
<script setup>
import { ref, provide, onMounted } from 'vue';
import Child1 from './Child1.vue'
import Child2 from './Child2.vue';
const title = ref('happy')
provide('title', title)
onMounted(()=>{
setTimeout(()=>{
title.value = 'hello'
},2000)
})
</script>
<style lang="css">
</style>
<template>
<div>
{{title}} Child1
</div>
</template>
<script setup>
//局部注册组件
import { ref, inject } from 'vue';
const title = inject('title')
</script>
<style lang="css">
</style>
<template>
<div>
{{title}} Child2
<Grandson></Grandson>
</div>
</template>
<script setup>
//局部注册组件
import { ref, inject } from 'vue';
import Grandson from './Grandson.vue';
const title = inject('title')
</script>
<style lang="css">
</style>
<template>
<div>
{{title}} Grandson
</div>
</template>
<script setup>
//局部注册组件
import { ref, inject } from 'vue';
const title = inject('title')
</script>
<style lang="css">
</style>
18-composition-functions
组合式函数
<template>
<div>
{{ count }}
<button @click="handelClick">add</button>
</div>
</template>
<script setup>
import userCount from './userCount'
import userTitle from './userTitel'
const {count, handelClick} = userCount()
userTitle(count)
</script>
<style lang="css">
</style>
import {ref} from 'vue'
const userCount = ()=>{
const count = ref(0)
const handelClick = () => {
count.value ++
}
return {
count,
handelClick
}
}
export default userCount
import { ref, onMounted, onUpdated } from 'vue';
const userTitle =(count)=>{
onMounted(()=>{
document.title = count.value
})
onUpdated(()=>{
document.title = count.value
})
}
export default userTitle
19-directive-plugin
自定义指令和插件
20-router
路由
21-pinia
状态管理pinia
<template>
<div>
<!-- {{counterStore.count}}
<p><button @click="counterStore.add()">add</button></p> -->
{{count}}
<p>{{title}}</p>
<p><button @click="counterStore.add()">add</button></p>
<Child></Child>
</div>
</template>
<script setup>
import {storeToRefs} from 'pinia' //storeToRefs将失去响应性的数据恢复响应性
import useCounterStore from '../../store/counterState'
import Child from './Child.vue'
const counterStore = useCounterStore()
const {count, title} = storeToRefs(counterStore)
</script>
<style lang="scss">
</style>
<template>
<div>
Child
<p>
{{title}} --- {{count}}
</p>
</div>
</template>
<script setup>
//局部注册组件
import useCounterStore from '@/store/counterState';
import { storeToRefs } from 'pinia'; //storeToRefs将失去响应性的数据恢复响应性
const countStore = useCounterStore()
const {count, title} = storeToRefs(countStore)
</script>
<style lang="css">
</style>
import {defineStore} from 'pinia'
const useCounterStore = defineStore('counterStore',{
state(){
return {
count: 0,
title: 'hello world'
}
},
actions: {
add(){
this.count ++
}
}
})
export default useCounterStore

浙公网安备 33010602011771号