vue(李仁杰)"/>
vue(李仁杰)
什么是 Vue?
Vue (发音为 /vjuː/,类似 view) 是一款用于构建用户界面的 JavaScript 框架。它基于标准 HTML、CSS 和 JavaScript 构建,并提供了一套声明式的、组件化的编程模型,帮助你高效地开发用户界面。无论是简单还是复杂的界面,Vue 都可以胜任。
快速入门
基本案例
效果为单击button按钮 count++
import { createApp } from 'vue'createApp({data() {return {count: 0}}}).mount('#app')
<div id="app"><button @click="count++">Count is: {{ count }}</button>
</div>
文本插值
最基本的数据绑定形式是文本插值,它使用的是“Mustache”语法 (即双大括号):
<span>Message: {{ msg }}</span>
双大括号标签会被替换为相应组件实例中 msg 属性的值。同时每次 msg 属性更改时它也会同步更新。
{{ }}里可以可以使用javascript表达式
{{ number +1}}
{{ ok ?'YES':'NO'}}
{{ message.split('').reverse().join('') }}
原始 HTML
双大括号会将数据解释为纯文本,而不是 HTML。若想插入 HTML,你需要使用 v-html指令:
<!-- v-html=innerHtml -->
<div v-html="html"></div>
v-html 会将html标签渲染
v-text 和 {{}} 不会渲染HTML标签,而是将标签和标签里的内容以纯文本的方式原样输出
绑定事件
可以使用 v-on 指令 (简写为 @) 来监听 DOM 事件,并在事件触发时执行对应的 JavaScript。用法:v-on:事件(如:click,change …)=“调用的JavaScript方法” 或 @click=“handler”
事件处理器的值可以是:
- 内联事件处理器:事件被触发时执行的内联 JavaScript 语句 (与 onclick 类似)。
- 方法事件处理器:一个指向组件上定义的方法的属性名或是路径。
事件处理
常用:
:::info
stop 阻止事件冒泡
prevent 取消事件默认行为 可以取消a标签的默认行为
once 只执行一次
:::
<div id="out_box" @click="out()"><div id="inner_box" @click.stop="getMsg()"><a href="" id="lrj" @click.once.prevent="getMsg2">孤独患者请自愈</a></div><a href="" id="lrj" @click.prevent @click.once="getMsg2">孤独患者请自愈</a>
</div>
数据绑定
数据绑定的一个常见需求场景是操纵元素的 CSS class 列表和内联样式。因为 class 和 style 都是 attribute,我们可以和其他 attribute 一样使用 v-bind 将它们和动态的字符串绑定。但是,在处理比较复杂的绑定时,通过拼接生成字符串是麻烦且易出错的。因此,Vue 专门为 class 和 style 的 v-bind 用法提供了特殊的功能增强。除了字符串外,表达式的值也可以是对象或数组。
- 绑定对象绑定对象
我们可以给 :class (v-bind:class 的缩写) 传递一个对象来动态切换 class:
<div :class="{ active: isActive }"></div>
上面的语法表示 active 是否存在取决于数据属性 isActive 的真假值。
- 绑定数组
我们可以给 :class 绑定一个数组来渲染多个 CSS class:
data() {return{ activeClass:'active', errorClass:'text-danger'}}
<div :class="[activeClass, errorClass]"></div>
渲染的结果是:
template<div class="active text-danger"></div>
v-if
v-if 指令用于条件性地渲染一块内容。这块内容只会在指令的表达式返回真值时才被渲染
<img alt="Vue logo" src="./assets/logo.png" :title="msg" v-if="aaa"><img alt="Vue logo" src="./assets/logo.png" :title="msg" v-if="bbb">
true 渲染 false buxuanran
data() {return {aaa: false,bbb: true}
v-else
可以使用 v-else 为 v-if 添加一个“else 区块”。
<span v-if="age>=18">十八岁</span>
<span v-else>不是十八</span>
渲染结果为显示十八岁
data(){return {age=18}
}
一个 v-else 元素必须跟在一个 v-if 或者 v-else-if 元素后面,否则它将不会被识别。
v-else-if
提供的是相应于 v-if 的“else if 区块”。它可以连续多次重复使用:
<span v-if="age>18">已成年</span>
<span v-else-if="age<18">未满十八</span>
<span v-else>十八</span>
渲染结果为 ”十八“
data(){return {age=18}
}
一个使用 v-else-if 的元素必须紧跟在一个 v-if 或一个 v-else-if 元素后面。
v-show
一个可以用来按条件显示一个元素的指令是 v-show。
<img alt="Vue logo" src="./assets/logo.png" :title="msg" v-show="aaa"><button @click="change">显示</button>
change(){this.aaa= this.aaa === true ? false :true
}
v-show 不支持在 元素上使用,也不能和 v-else 搭配使用。
注意:
- v-show 控制css样式是否displat
- v-if 控制标签是否渲染
v-for
v-for 指令基于一个数组来渲染一个列表。v-for 指令的值需要使用 item in items 形式的特殊语法,其中 items 是源数据的数组,而 item 是迭代项的别名:
<ul v-for="name in names" :key="name"><li v-text="name"></li>
</ul>//通过下标<!--第一个参数是列表元素,第二个参数是列表索引--><ul v-for="(name,index) in names" :key="name + index"><li v-text="names[index]"></li></ul>
<!--第一个参数是对象属性值,第二个参数是对象属性名--><div v-for="(value,key) in person" v-text="key+':'+value" :key="key">
<table><!--person 集合里对象别名 persons集合名--><!--通过对象名.对象属性名的方式去遍历--><tr v-for="person in persons" :key="person.id"><td v-text="person.name"></td><td v-text="person.age"></td></tr></table>
计算属性 (computed)
写在 computed里
computed: {msg() {return '她说彩礼八十万';},
通过getter\setter实现对属性数据的显示和监视,计算属性存在缓存,多次读取只执行一次getter计算。
监听器 watch
watch: {/*** 监听器* @param newValue 新值 变化后的值* @param oldValue 旧值 变化前的值*/slogan(newValue, oldValue) {console.log(newValue,oldValue)}
team:{handler(){this.battle();},//初始化时调用immediate:true,//是否深度监听//deep:true}
表单操作
v-model
双向数据绑定(数据改变,渲染视图)
在前端处理表单时,我们常常需要将表单输入框的内容同步给 JavaScript 中相应的变量。手动连接值绑定和更改事件监听器可能会很麻烦:
<input:value="text"@input="event => text = event.target.value">
v-model 指令帮我们简化了这一步骤:
<input v-model="text">
另外,v-model 还可以用于各种不同类型的输入,、 元素。它会根据所使用的元素自动使用对应的 DOM 属性和事件组合:
- 文本类型的 和 元素会绑定 value property 并侦听 input 事件;
- 和 会绑定 checked property 并侦听 change 事件;
- 会绑定 value property 并侦听 change 事件。
注意
:::info
v-model 会忽略任何表单元素上初始的 value、checked 或 selected attribute。它将始终将当前绑定的 JavaScript 状态视为数据的正确来源。你应该在 JavaScript 中使用data 选项来声明该初始值。
:::
基本用法
文本
{{slogan}}<span v-text="slogan"></span><input type="text" v-model="slogan">
data() {return {slogan: '她说彩礼八十万'}
}
多行文本
<span>文本框输入内容:</span>
<p style="white-space: pre-line;">{{ message }}</p>
<textarea v-model="message" placeholder="输入内容"></textarea>
注意在 中是不支持插值表达式的。请使用 v-model 来替代:
<!-- 错误 -->
<textarea>{{ text }}</textarea><!-- 正确 -->
<textarea v-model="text"></textarea>
复选框
单一的复选框,绑定布尔类型值:
<input type="checkbox" id="checkbox" v-model="checked" />
<label for="checkbox">{{ checked }}</label>
单选按钮
<div>选择: {{ picked }}</div><input type="radio" id="one" value="One" v-model="picked" />
<label for="one">One</label><input type="radio" id="two" value="Two" v-model="picked" />
<label for="two">Two</label>
多选按钮
可以将多个复选框绑定到同一个数组或集合的值:
<input type="checkbox" id="" name="aihao" value="" v-model="hobbies">游泳<input type="checkbox" id="" name="aihao" value="run" v-model="hobbies">跑步<input type="checkbox" id="" name="aihao" value="skiing" v-model="hobbies">滑雪{{
data() {return {hobbies:['run','skiing']}
}
单选下拉列表框
<select name="hometown" v-model="hometown"><option value="beijing">北京</option><option value="henan">河南</option><option value="hebei">河北</option>
</select>{{hometown}}
多选下拉列表
<select name="hometown" v-model="hometown" multiple><option value="beijing">北京</option><option value="henan">河南</option><option value="hebei">河北</option>
</select>{{hometown}}
v-model修饰符
.trim
如果想要默认自动去除用户输入内容中两端的空格,你可以在 v-model 后添加 .trim 修饰符:
{{slogan}}
<input type="text" v-model.trim="slogan">
.lazy
默认情况下,v-model 会在每次 input 事件后更新数据。可以添加 lazy 修饰符来改为在每次 chang 事件后更新数据:
<span v-text="slogan"></span>
<input type="text" v-model.trim.lazy="slogan">
.number
如果你想让用户输入自动转换为数字,你可以在 v-model 后添加 .number 修饰符来管理输入:
<input type="text" v-model.number="age">
如果该值无法被 parseFloat() 处理,那么将返回原始值。
number 修饰符会在输入框有 type=“number” 时自动启用。
组件基础
组件允许我们将 UI 划分为独立的、可重用的部分,并且可以对每个部分进行单独的思考。在实际应用中,组件常常被组织成层层嵌套的树状结构:
这和我们嵌套 HTML 元素的方式类似,Vue 实现了自己的组件模型,使我们可以在每个组件内封装自定义内容与逻辑。Vue 同样也能很好地配合原生 Web Component
1. 如何导入组件
- 定义组件
<template><h1 v-text="slogan"></h1>
</template>
<script>export default {name: "Demo",data(){return{slogan:'孤独患者请自愈'}},}
</script>
- 引入组件
<template><Demo></Demo>
</template>
<script>//引⼊组件import Demo from "@/components/demo/Demo";export default {name: 'App',components:{Demo}}
</script>
组件传值
父传子
- 在⽗组件定义⼀个值
<Demo msg="她说彩礼⼋⼗万"></Demo>
- 接收值
props:{msg:{type:String,//必须接收值request:true,//没有值的情况下 设置默认值default:'她说彩礼八十万'}
}
子传父
- 定义⼀个⼦组件
<template><button type="button" v-text="innerSlogan" @click="my"></button>
</template>
<script>export default {name: "Demo2",data(){return{innerSlogan:"郁金香没她郁金香"}},//定义⼀个⽅法methods:{my(){//第⼀个参数发送出去的动作 第⼆次参数是该动作携带的值this.$emit('my',this.innerSlogan)}}}
</script>
- 接收
<template><span v-text="slogan"></span><span v-text="msg"></span><Demo2 @my="my"></Demo2></template>
<script>import Demo2 from "@/components/demo/Demo2";export default {name: "Demo",data(){return{slogan:'嗨害'}},props:{msg:{type:String,request:true,default:'盛夏亦是她'}},components:{Demo2},methods:{my(content){this.slogan=content;}}}
</script>
运行步骤 首先子元素发送了⼀个叫动作叫my,并携带了参数,然后根据⼦组件的click的单机事件发送出去,然后父组 件捕获子组件传送的值
父子组件表单传值
<template>>>>父组件表单<input type="text" v-model="username"><br><HelLrj :parent="username" @getSubValue="username=$event"></HelLrj><br><hr><!--触发函数--><HelLrj :parent="username" @getSubValue="subValue"></HelLrj><LrjA v-model:parent="username"></LrjA>
</template><script>
import HelLrj from "@/components/chao05/HelLrj";
import LrjA from "@/components/chao05/LrjA";
export default {name: 'App',components: {HelLrj,LrjA},data() {return {username: ''}},methods: {subValue(value) {this.username=value}}
}
</script>
<template>>>>子组件表单 :value绑定<input type="text" :value="parent" @input="$emit('getSubValue',$event.target.value)"><br>>>>子组件 v-model 绑定<input type="text" v-model="parentValue" @input="$emit('getSubValue',$event.target.value)"><br></template><script>export default {name: "HelLrj",props: {parent: {type: String}},computed:{parentValue() {return this.parent;}}}
</script>
<template><input type="text" :value="parent" @input="$emit('update:parent',$event.target.value)"><br>
</template><script>
export default {name: "LrjA",props:{parent:{type:String}}
}
</script>
slot插槽
<template>
<HelLrj ref="HelLrj">lirenjie
</HelLrj>
</template><script>
import HelLrj from "@/components/chao06/HelLrj";
export default {name: 'App',components: {HelLrj}
}
</script>
子组件标签里的内容会显示在子组件标签位置
<template><slot></slot>
<h1>她说彩礼八十万</h1><slot></slot>
</template>
<script>
export default {name: "HelLrj"
}
</script>
具名插槽
<template><HelLrj ref="HelLrj"><template v-slot:default>lirenjie</template>
<template v-slot:nva>残情
</template>
<template v-slot:foot>孤独患者
</template>
</HelLrj></template><script>import HelLrj from "@/components/chao06/HelLrj";export default {name: 'App',components: {HelLrj},</script>
会找相对应的 v-slot:‘name’,没有name就找defaule(默认)
<template><slot name="nva"></slot><h1>她说彩礼八十万</h1><slot name="foot"></slot><slot></slot>
</template><script>export default {name: "HelLrj"}
</script>
插槽缩写与插槽传值
- 插槽缩写
<HelLrj ref="HelLrj"><template #lrj>插槽缩写</template>
</HelLrj>
</template>
#+name定义 使用
<template><slot name="lrj"></slot>
</template><script>export default {name: "HelLrj"}
</script>
插槽传值
<template><slot name="set" :names="names"></slot>
</template>
<script>export default {name: "HelLrj",data(){return{names:['lrj','gzy','zn']}}}
</script>
绑定属性传值,传过去的是对象属性名,
<template><HelLrj ref="HelLrj"><!--插槽传值--><template #set="lrjData"><div v-text="lrjData"></div><div v-for="(name,index) in lrjData.names" :key="name+index" v-text="name"></div></template></HelLrj>
</template><script>import HelLrj from "@/components/chao06/HelLrj";export default {name: 'App',components: {HelLrj},</script>
使用解构赋值的方式进行插槽传值
<template><slot name="set" :names="names"></slot>
</template>
<script>export default {name: "HelLrj",data(){return{names:['lrj','gzy','zn']}}}
</script>
{ 属性名 } 绑定的属性名结构取值
<template><HelLrj ref="HelLrj"><template #set="{names}"><div v-text="names"></div><div v-for="(name,index) in names" :key="name+index" v-text="name"></div></template></HelLrj>
</template>
<script>import HelLrj from "@/components/chao06/HelLrj";export default {name: 'App',components: {HelLrj},</script>
组件深入
依赖注入
解决props逐级透传问题
通常情况下,当我们需要从父组件向子组件传递数据时,会使用 props。想象一下这样的结构:有一些多层级嵌套的组件,形成了一颗巨大的组件树,而某个深层的子组件需要一个较远的祖先组件中的部分数据。在这种情况下,如果仅使用 props 则必须将其沿着组件链逐级传递下去,这会非常麻烦:
provide 和 inject 可以帮助我们解决这一问题。一个父组件相对于其所有的后代组件,会作为依赖提供者。任何后代的组件树,无论层级有多深,都可以注入由父组件提供给整条链路的依赖
案例
<template><h1>SOLRJ</h1><button @click="changeSlogan">改变slogan</button><button @click="changeObj">改变Obj</button><div v-text="slogan"></div><div v-text="obj.slogan"></div><LrjM></LrjM>
</template><script>
import LrjM from "@/components/chao07/LrjM";export default {name: "SOLRJ",components: {LrjM},data() {return {slogan: '她说彩礼八十万',obj: {slogan: '她说彩礼八十万'}}},// provide:{// slogan: '她说彩礼八十万'// }provide() {return {//使用函数的形式可以访问thisslogan: '她说彩礼八十万',obj: this.obj,msg: () => {return this.slogan;}}}, methods: {changeSlogan() {this.slogan = '孤独患者请自愈'},changeObj() {this.obj.slogan = '孤独患者请自愈'}}}
</script>
<template><h1>LrjM</h1><LrjN></LrjN><hr><LrjN2></LrjN2>
</template><script>
import LrjN from "@/components/chao07/LrjN";
import LrjN2 from "@/components/chao07/LrjN2";
export default {name: "LrjM",components: {LrjN,LrjN2}}
方式一
<template><h1>LrjN</h1><div v-text="slo"></div><div v-text="person.slogan"></div><div v-text="getMsg"></div>
</template><script>
export default {name: "LrjN",inject:['slogan','obj','msg'],computed:{slo(){return this.slogan},person(){return this.obj},getMsg(){return this.msg();}}
}
</script>
方式二
<template><h1>LrjN2</h1><div v-text="slo"></div><div v-text="person.slogan"></div><div v-text="getMsg"></div>
</template><script>
export default {name: "LrjN2",// inject:['slogan','obj','msg'],//对象方式注入injectinject: {slogan: {from: 'slogan',default: ''},obj: {from: 'obj',default: {}},msg: {from: 'msg',default: () => {return ''}}},computed: {slo() {return this.slogan},person() {return this.obj},getMsg() {return this.msg();}}
}
</script>
vue动画基础
入门案例
实现鼠标悬停div旋转,鼠标离开div恢复
<template><div id="box" :class="{me:isMe}" @mouseenter="isMe=!isMe" @mouseleave="isMe=!isMe"></div>
</template><script>
export default {name: "LrjA",data() {return {isMe: false}}}
</script><style scoped>
#box {width: 450px;height: 450px;background-color: #00aa00;position: absolute;top: 100px;left: 100px;transition: 500ms;
}.me {transform: rotate(45deg);
}
</style>
transtion基本使用
给transtion绑定name属性,绑定的css样式都使用name做前缀
<template><button @click="isShow=!isShow">显示|隐藏</button><transition name="lrj"><div class="box" :class="{me:isMe}" @mouseenter="isMe=!isMe" @mouseleave="isMe=!isMe" v-show="isShow"></div></transition></template><script>
export default {name: "LrjA",data() {return {isMe: false,isShow:true}}}
</script><style scoped>
.box {width: 450px;height: 450px;background-color: #00aa00;position: absolute;top: 100px;left: 100px;transition: 500ms;
}.me {transform: rotate(45deg);
}
/*进入前*/
.lrj-enter-from{width: 0px;height: 0px;
}
/*进入中*/
.lrj-enter-active{
transition: 3s all ease;
}
/*进入完成*/
.lrj-enter-to{width: 450px;height: 450px;
}
/*离开之前*/
.lrj-leave-form{width: 450px;height: 450px;
}
/*离开中*/
.lrj-leave-active{transition: 3s all ease;
}
/*离开完成*/
.lrj-leave-to{width: 0px;height: 0px;
}</style>
transtion自定义类名
<template><button @click="isShow=!isShow">显示|隐藏</button><transition name="lrj"enter-from-class="enter-from"enter-active-class="enter-active"enter-to-class="enter-to"leave-from-class="leave-from"leave-active-class="leave-active"leave-to-class="leave-to"><div class="box" :class="{me:isMe}" @mouseenter="isMe=!isMe" @mouseleave="isMe=!isMe" v-show="isShow"></div></transition></template><script>
export default {name: "LrjA",data() {return {isMe: false,isShow: true}}}
</script><style scoped>
.box {width: 450px;height: 450px;background-color: #00aa00;position: absolute;top: 100px;left: 100px;transition: 500ms;
}.me {transform: rotate(45deg);
}/*进入前*/
.enter-from {width: 0px;height: 0px;
}/*进入中*/
.enter-active {transition: 3s all ease;
}/*进入完成*/
.enter-to {width: 450px;height: 450px;
}/*离开之前*/
.leave-form {width: 450px;height: 450px;
}/*离开中*/
.leave-active {transition: 3s all ease;
}/*离开完成*/
.leave-to {width: 0px;height: 0px;
}</style>
transtion生命周期函数
<transition name="lrj"enter-from-class="enter-from"enter-active-class="enter-active"enter-to-class="enter-to"leave-from-class="leave-from"leave-active-class="leave-active"leave-to-class="leave-to"@before-enter="beforeEnter"@enter="enter"@after-enter="afterEnter"@before-leave="beforeLeave"@leave="leave"@after-leave="afterLeave":duration="{enter:5000,leave:5000}":css="true">
进入前 @before-enter @before-leave=“beforeLeave” 离开前
进入中 @enter=“enter” @leave=“leave” 离开中
进入后 @after-enter=“afterEnter” @after-leave=“afterLeave” 离开后
参数
:duration = {enter:进入时延(毫秒数),leave:离开时延(毫秒数)}
:css = {boolean值} 是否启动css样式
enter(element,done) {//element调用函数的对象//done是一个函数 可以在函数中延时调用函数console.log(element)setTimeout(()=>{done();},5000);
}leave(element,done) {console.log(element)setTimeout(()=>{done();},5000);}
transtion初始化过渡
<transition name="lrj"appearappear-class="appear-from"appear-active-class="appear-active"appear-to-class="appear-to"><div class="box" :class="{me:isMe}" @mouseenter="isMe=!isMe" @mouseleave="isMe=!isMe" v-show="isShow"></div>
</transition>
transtion多元素渲染
默认不允许多元素渲染
<template><button @click="isShow=!isShow">显示|隐藏</button><div v-text="info"></div><transition name="lrj"appearappear-class="appear-from"appear-active-class="appear-active"appear-to-class="appear-to"enter-from-class="enter-from"enter-active-class="enter-active"enter-to-class="enter-to"leave-from-class="leave-from"leave-active-class="leave-active"leave-to-class="leave-to"@before-enter="beforeEnter"@enter="enter"@after-enter="afterEnter"@before-leave="beforeLeave"@leave="leave"@after-leave="afterLeave":duration="{enter:5000,leave:5000}":css="true"><div class="box a" :class="{me:isMe}" @mouseenter="isMe=!isMe" @mouseleave="isMe=!isMe" v-if="isShow"></div><div class="box b" :class="{me:isMe}" @mouseenter="isMe=!isMe" @mouseleave="isMe=!isMe" v-else></div></transition>
v-if 两个div只会渲染一个
transition过度模式
<button class="box" style="background-color: #4365c3" type="button" @click="toggle">状态切换</button>
<transitionmode="out-in"enter-from-class="enter-from"leave-to-class="leave-to"><div class="box on" v-if="isShow">设备开机</div><div class="box off" v-else>设备关机</div>
</transition>
</template><script>export default {name: "HelloLrj",data() {return {isShow: true}}, methods: {toggle() {this.isShow = !this.isShow}}}
</script>
过度模式设置 mode 两个值:1.in-out 先进后厨
2.out-in 先出后进
transition多组件过度
默认不允许多组件渲染,使用v-if v-else 来控制 之渲染一个
<template>
<button @click="toggle" type="button">更改状态</button><transitionmode="out-in"enter-from-class="enter-from"leave-to-class="leave-to"><LrjOn ref="lrjOn" v-if="isOn"></LrjOn><LrjOff ref="lrjOff" v-else></LrjOff></transition>
</template><script>
import LrjOn from "@/components/chao09/LrjOn";
import LrjOff from "@/components/chao09/LrjOff";export default {name: "HelloLrj",components: {LrjOn,LrjOff},data() {return {isOn: true,}}, methods: {toggle() {this.isOn = !this.isOn}}
}
</script>
<template><div class="box on">设备开机</div>
</template><script>
export default {name: "LrjOn"
}
</script>
<template><div class="box off">设备关机</div>
</template><script>
export default {name: "LrjOff"
}
</script>
transition-group
案例
随机添加删除
<template><button @click="add">添加</button><button @click="del">删除</button><transition-groupenter-active-class="animate__animated animate__zoomInDown"leave-active-class="animate__animated animate__zoomOutUp"><div class="lrj" v-for="num in nums" :key="num" v-text="num"></div></transition-group></template><script>export default {name: "LrjA",data() {return {nums: [1, 2, 4, 5, 6, 7, 8, 9],//参考值reference: 10,}}, methods: {add() {//向下取整this.nums.splice(Math.floor(Math.random() * this.nums.length), 0, this.reference++)},del() {//向下取整this.nums.splice(Math.floor(Math.random() * this.nums.length), 1)}}}
</script><style scoped>button {width: 200px;height: 200px;font-size: 66px;}.lrj {float: left;margin-top: 115px;margin-left: 15px;width: 60px;height: 60px;text-align: center;line-height: 60px;background-color: #123456;color: #ffffff;}
</style>
如何在vue中使用animate.css
- 安装animate.css
npm install animate.css --save
- 在main.js中引入animate.css
import ‘animate.css’
案例
<template><button type="button" @click="isShow=!isShow">显示隐藏</button><transitionenter-active-class="animate__animated animate__rollIn"leave-active-class="animate__animated animate__rollOut"><div class="lrj" v-if="isShow"></div></transition>
</template><script>export default {name: "LrjAnimate",data() {return {isShow: true}},}
</script><style scoped>.lrj {width: 600px;height: 600px;background-color: #00aa00;}button {width: 300px;height: 300px;font-size: 66px;}
</style>
如何在vue中使用gsap
- 安装gsap
终端输入
npm install gsap --save
案例
<template><button type="button" @click="isShow=!isShow">显示隐藏</button><transition @enter="fromTo" @leave="to" :duration="{enter:3000,leave:3000}"><div v-if="isShow"></div></transition>
</template><script>
//引入gsap函数
import {gsap} from "gsap";export default {name: "LrjGsap",data() {return {isShow: false}}, methods: {from(element) {//第一个参数是要操作的dom元素、//第二个参数是动画的参数属性gsap.from(element, {x: 300,backgroundColor: '#ff0000',duration: 3})}, to(element) {gsap.to(element, {x: 300,backgroundColor: '#ff0000',duration: 3})}, fromTo(element) {第一个参数是要操作的dom元素、//第二,三个参数是进入/离开动画的参数属性gsap.fromTo(element, {x: 300,backgroundColor: '#ff0000',duration: 3,width: 100,height: 100}, {x: 600,backgroundColor: '#00ffff',duration: 3,width: 300,height: 300})}}
}
</script><style scoped>
.lrj {width: 300px;height: 300px;background-color: #00aa00;
}
</style>
gsap在vue中的基本应用
<template><button @click="add">添加</button><button @click="del">删除</button><transition-group@enter="enter"@leave="leave" :duration="{enter:1000,leave:1000}"><div class="lrj" v-for="num in nums" :key="num" v-text="num"></div></transition-group></template><script>
import {gsap} from "gsap";export default {name: "LrjA",data() {return {nums: [1, 2, 4, 5, 6, 7, 8, 9],//参考值reference: 10,}}, methods: {add() {//向下取整this.nums.splice(Math.floor(Math.random() * this.nums.length), 0, this.reference++)},del() {//向下取整this.nums.splice(Math.floor(Math.random() * this.nums.length), 1)},enter(el) {gsap.from(el, {width: 0,height: 0,fontSize: 0,duration: 1})},leave(el){gsap.to(el,{width: 0,height: 0,fontSize: 0,duration: 1})}}
}
</script><style scoped>
button {width: 200px;height: 200px;font-size: 66px;
}.lrj {float: left;margin-top: 115px;margin-left: 15px;width: 60px;height: 60px;text-align: center;line-height: 60px;background-color: #123456;color: #ffffff;
}
</style>
veu中gsap综合案例
<template><div class="main"><div class="box" ref="box" v-for="n in count" :key="n"></div></div>
</template><script>import {gsap} from "gsap";export default {name: "LrjC",data() {return {count: 170}},mounted() {let box = this.$refs['box'];gsap.to(box, {//缩放为0.1scale: 0.1,y: 60,yoyo: true,//如果该值为true,则每隔一次重复补间将朝相反的方向运行。(像溜溜球一样)默认false,repeat :-1 ,//数值是几重复几次 0 不重复 1 一次 -1 一直重复,delay: 1, //延迟多长时间执行 (在这个案例为1秒)//每个目标动画开始之间的事件(以秒为单位)(如果提供了多个目标)stagger: {amount: 1.5,//补的时间差grid:"auto",//运动的方式from:"center"//(中心)从那开始运动}})}}
</script><style scoped>html,body{height: 100%;}body{background-color: #1d1d1d;font-family: "Signika Negative",sans-serif;color: #989898;margin: 0 10px;font-size: 17px;text-align: center;}#app{font-family: Avenir, Helvetica, Arial, sans-serif;-webkit-font-smoothing: antialiased;-moz-osx-font-smoothing: grayscale;text-align: center;color: #2c3e50;}.main{max-width: 1200px;height: 100%;position: relative;display: inline-block;}.box{width: 50px;height: 50px;position: relative;border-radius: 0px;margin-top: 4px;display: inline-block;margin: 0px 1.5% 11.5% 0px;background-color: #6fb936;}
</style>
Vite 下一代的前端工具链 为开发提供极速响应
搭建第一个Vite项目
兼容性注意
Vite 需要 Node.js 版本 14.18+,16+。然而,有些模板需要依赖更高的 Node 版本才能正常运行,当你的包管理器发出警告时,请注意升级你的 Node 版本。
使用nmp搭建
npm create vite@latest+ 项目名称
选择Vue 按enter键
选择语言 JavaScript 按enter键
根据提示 一步步操作
cd mtVue-vite 进入项目
npm install 下载安装依赖
npm run dev 运行项目
http://127.0.0.1:5173/ 访问
WebStrom配置Vite项目
- WebStrom 打开一个Vite
- 配置npm 脚本输入 dev
vite项目引入子组件
- 定义子组件
<template><H1>孤独患者请自愈</H1>
</template><script>export default {name: "LrjA"}
</script><style scoped></style>
- 引入子组件
import LrjA from "./components/LrjA.vue";</script><template><LrjA></LrjA></template>
setup函数
<template><H1>孤独患者请自愈</H1><h1 v-text="dataSlogan"></h1><button type="button" @click="changeDataSlogan">改变dataSlogan</button>
</template><script>export default {name: "LrjA",data() {return {dataSlogan: 'dataSlogan'}}, methods: {changeDataSlogan() {this.dataSlogan = 'newDataSlogan'}}}
</script><style scoped></style>
<template><H1>孤独患者请自愈</H1><h1 v-text="setupSlogan"></h1><button type="button" @click="changeSetupSlogan">改变setupSlogan</button>
</template><script>import {ref} from "vue";export default {name: "LrjA",setup() {const setupSlogan = ref('setupSlogan') //此时setupSlogan是一个对象const changeSetupSlogan = () => {setupSlogan.value = 'newSetSlogan' //为对象的value赋值}return { //返回对象setupSlogan,changeSetupSlogan}}}
</script><style scoped></style>
引用类型操作
setup操作引用类型
<template><H1>孤独患者请自愈</H1><h1 v-text="obj.name"></h1><h1 v-text="obj.slogan"></h1><button type="button" @click="changeObj">改变Obj</button>
</template><script>//导入ref组件import {ref} from "vue";export default {name: "LrjA",setup() {const obj = ref({name: '烟雨过客',slogan: '她说彩礼八十万'})const changeObj = () => {obj.value.name = '天下无双'obj.value.slogan = '只是过往,是过往'}return { //返回对象 obj,changeObj}}}
</script><style scoped></style>
recative操作应用类型
<template><H1>孤独患者请自愈</H1><h1 v-text="obj.name"></h1><h1 v-text="obj.slogan"></h1><button type="button" @click="changeObj">改变Obj</button>
</template><script>//导入ref和recative组件 import {ref,reactive} from "vue";export default {name: "LrjA",setup() {const obj = reactive({name: '烟雨过客',slogan: '她说彩礼八十万'})const changeObj = () => {obj.name = '天下无双'obj.slogan = '只是过往,是过往'}return { //返回对象obj,changeObj}}}
</script>
setup函数的props传值
第一种方法 setup利用props传值
<template><LrjC :msg="msg" :person="person"></LrjC>
</template><script>import {ref, reactive} from "vue";import LrjC from "./LrjC.vue";export default {name: "LrjB",components:{LrjC},setup() {const msg = ref('我爱你')const person = reactive({raleName: 'AJIE',slogan: '残情'})return{msg,person}}}
</script><style scoped></style>
<template><h1 v-text="msg"></h1><h1 v-text="person.slogan"></h1><h1 v-text="person.raleName"></h1></template><script>export default {name: "LrjC",props: ['msg', 'person'],setup(props) {console.log(props.msg)console.log(props.person.slogan)console.log(props.person.raleName)}}
</script><style scoped></style>
第二种 setup函数利用defineProps传值
<template><LrjC :msg="msg" :person="person"></LrjC>
</template>
<script setup>import LrjC from "./LrjC.vue";const msg = '我爱你'const person = {raleName: 'AJIE',slogan: '残情'}
</script>
<script>export default {name: "LrjB",}
</script><style scoped></style>
<template><h1 v-text="msg"></h1><h1 v-text="person.slogan"></h1><h1 v-text="person.raleName"></h1></template>
<script setup>defineProps(['msg','person'])
</script>
<script>export default {name: "LrjC",}
</script><style scoped></style>
setup函数context_attrs传值
<template><LrjC :msg="msg" :person="person"></LrjC>
</template><script>import {ref, reactive} from "vue";import LrjC from "./LrjC.vue";export default {name: "LrjB",components:{LrjC},setup() {const msg = ref('我爱你')const person = reactive({raleName: 'AJIE',slogan: '残情'})return{msg,person}}}
</script><style scoped></style>
<template><h1 v-text="attrs.msg"></h1><h1 v-text="attrs.person.slogan"></h1><h1 v-text="attrs.person.raleName"></h1></template><script>export default {name: "LrjC",// props: ['msg', 'person'],setup(props,context) {// console.log(context.attrs)//解构赋值的方式取值let {attrs} = context;return{attrs}}}
</script><style scoped></style>
setup函数 context_emit 传值
<template>
<h1 v-text="attrs.msg"></h1>
<h1 v-text="attrs.person.slogan"></h1>
<h1 v-text="attrs.person.raleName"></h1>
<button type="button" @click="updateName">子组件传值</button>
</template><script>
import {ref} from "vue";
export default {name: "LrjC",// props: ['msg', 'person'],setup(props,context) {// console.log(context.attrs)//解构赋值的方式取值let {attrs,emit} = context;const myName = ref('老K')const updateName = function () {emit('updateName',myName)}return{attrs,updateName}}
}
</script><style scoped></style>
子组件点击按钮调用自定义方法,父组件捕获动作,调用父组件自定义方法 ,将传过来的参数赋值给父组件属性
<template>
<LrjC :msg="msg" :person="person" @updateName="updateName"></LrjC>
</template><script>
import {ref, reactive} from "vue";
import LrjC from "./LrjC.vue";
export default {name: "LrjB",components:{LrjC},setup() {const msg = ref('我爱你')const person = reactive({raleName: 'AJIE',slogan: '残情'})const updateName = function (value){person.raleName=value;}return{msg,person,updateName}}
}
</script><style scoped></style>
setup函数 defineEmits 传值
<template><h1 v-text="msg"></h1><h1 v-text="person.raleName"></h1><h1 v-text="person.slogan"></h1><button type="button" @click="updateName">点击改变</button>
</template>
<script setup>import {ref} from "vue";defineProps(['msg','person']);//自定义发送动作const emit = defineEmits(['update']);//自定义发送参数const myName = ref('老K')const updateName=function (){//发射自定义动作,并携带参数emit('update',myName)}
</script>
<script>export default {name: "LrjE",}
</script><style scoped></style>
执行的操作:子组件点击事件调用自定义方法,自定义方法将自定义动作并携带发射给父组件,父组件捕获自定义动作,并调用自身方法,将发射过来的参数,赋值给父组件属性
<template><h1 v-text="person.raleName"></h1><LrjE :msg="msg" :person="person" @update="updateName"></LrjE>
</template>
<script setup>import {ref,reactive} from "vue";import LrjE from "./LrjE.vue";const msg = ref('我爱你')const person = reactive({raleName: 'AJIE',slogan: '残情'})const updateName=function (value){person.raleName=value}
</script>
<script>export default {name: "LrjD",}
</script><style scoped></style>
setup函数context_slots插槽传值
<template><h1 v-text="slogan"></h1><LrjG><template #lrjAA><h1>lrj-aa</h1></template>
<template #lrjBB><h1>lrj-bb</h1>
</template>
<template #lrjCC><h1 v-text="slogan"></h1>
</template>
</LrjG><button type="button" @click="changeSlogan">改变slogan</button></template><script>import LrjG from "./LrjG.vue";import {ref} from "vue";export default {name: "LrjF",setup(){const slogan = ref('孤独患者请自愈');const changeSlogan = function (){this.slogan='她说彩礼八十万'}return{slogan,changeSlogan}},components:{LrjG}}
</script><style scoped></style>
<template><h1>LrjG</h1><slot name="lrjAA"></slot><slot name="lrjBB"></slot><slot name="lrjCC"></slot>
</template><script>import {ref} from "vue";export default {name: "LrjG",setup(props,context){const {slots}=context;//用函数的方式取slots//以下表的方式将内容取出// console.log(slots.lrjAA()[0].children)console.log(slots.lrjBB()[0].children)//修改slots.lrjBB()[0].children的值slots.lrjBB()[0].children='烟雨过客'console.log(slots.lrjBB()[0].children)}}
</script><style scoped></style>
父组件属性值修改 context_slots插槽传的值也会修改
更多推荐
vue(李仁杰)
发布评论