简介:
Vue2到3 Day1-3 全套学习内容,众多案例上手(内付源码)_星辰大海1412的博客-CSDN博客本文是一篇入门级的Vue.js介绍文章,旨在帮助读者了解Vue.js框架的基本概念和核心功能。Vue.js是一款流行的JavaScript前端框架,被广泛用于构建现代、响应式的Web应用。通过深入浅出的方式,文章将介绍Vue.js的基本概念,如组件、指令、双向数据绑定等,并演示如何使用Vue.js开发一个简单的示例应用。无论您是初学者还是有经验的前端开发者,本文都将为您提供一个良好的起点,让您能够迅速上手并充分利用Vue.js的强大功能https://blog.csdn.net/m0_61662775/article/details/131949855?spm=1001.2014.3001.5501
Vue2到3 Day4 全套学习内容,众多案例上手(内付源码)_星辰大海1412的博客-CSDN博客通过这篇文章了解Vue的响应式数据机制,以及如何使用data属性来实现数据驱动的界面更新。学习如何使用计算属性、侦听器等处理数据逻辑。https://blog.csdn.net/m0_61662775/article/details/132221004?spm=1001.2014.3001.5501
接下里的学习内容如下:
吾生也有涯,而知也无涯。学无止境,然犹需沉潜。兢兢业业,方能于浩瀚知识的汪洋中,稍觉安宁。加油!
一、自定义指令
1.指令介绍:
-
内置指令:v-html、v-if、v-bind、v-on... 这都是Vue内置的一些指令,可以直接使用
-
自定义指令:同时Vue也支持让开发者,自己注册一些指令。这些指令被称为自定义指令
每个指令都有自己各自独立的功能
2.自定义指令:
概念:自己定义的指令,可以封装一些DOM操作,扩展额外的功能
📜示例:
需求: 当页面加载时,让元素将获得焦点
(autofocus 在 safari 浏览器有兼容性)
操作dom: dom元素.focus()
mounted () {this.$refs.inp.focus()
}
3.自定义指令语法
1️⃣全局注册-语法:
//在main.js中
Vue.directive('指令名', {"inserted" (el) {// 可以对 el 标签,扩展额外功能el.focus()}
})
2️⃣局部注册-语法:
//在Vue组件的配置项中
directives: {"指令名": {inserted () {// 可以对 el 标签,扩展额外功能el.focus()}}
}
使用指令
⭕注意:在使用指令的时候,一定要先注册,再使用,否则会报错
使用指令语法: v-指令名。如:<input v-指令名 type="text">
注册指令时不用加v-前缀,但使用时一定要加v-前缀
代码示例:
//main.js 文件import Vue from 'vue'
import App from './App.vue'Vue.config.productionTip = false// // 1. 全局注册指令
// Vue.directive('focus', {
// // inserted 会在 指令所在的元素,被插入到页面中时触发
// inserted (el) {
// // el 就是指令所绑定的元素
// // console.log(el);
// el.focus()
// }
// })new Vue({render: h => h(App),
}).$mount('#app')
<template><div><h1>自定义指令</h1><input v-focus ref="inp" type="text"></div>
</template><script>
export default {// mounted () {// this.$refs.inp.focus()// }// 2. 局部注册指令directives: {// 指令名:指令的配置项focus: {inserted (el) {el.focus()}}}
}
</script><style></style>
4.指令中的配置项介绍:
inserted:被绑定元素插入父节点时调用的钩子函数
el:使用指令的那个DOM元素
5.代码示例:
需求:当页面加载时,让元素获取焦点(autofocus在safari浏览器有兼容性)
6.总结:
1.自定义指令的作用是什么?
2.使用自定义指令的步骤是哪两步?
自定义指令-指令的值
1.需求:
实现一个 color 指令 - 传入不同的颜色, 给标签设置文字颜色
2.语法:
①在绑定指令时,可以通过“等号”的形式为指令 绑定 具体的参数值
<div v-color="color">我是内容</div>
②通过 binding.value 可以拿到指令值,指令值修改会 触发 update 函数
directives: {color: {inserted (el, binding) {el.style.color = binding.value},update (el, binding) {el.style.color = binding.value}}
}
3.代码示例:
<template><div><h1 v-color="color1">指令的值1测试</h1><h1 v-color="color2">指令的值2测试</h1></div>
</template><script>
export default {data () {return {color1: 'red',color2: 'orange'}},directives: {color: {// 1. inserted 提供的是元素被添加到页面中时的逻辑inserted (el, binding) {// console.log(el, binding.value);// binding.value 就是指令的值el.style.color = binding.value},// 2. update 指令的值修改的时候触发,提供值变化后,dom更新的逻辑update (el, binding) {console.log('指令的值修改了');el.style.color = binding.value}}}
}
</script><style></style>
4.📜总结:
1.通过指令的值相关语法,可以应对更复杂指令封装场景
2.指令值的语法:
① v-指令名 ="指令值",通过 等号 可以绑定指令的值
② 通过 binding.value 可以拿到指令的值
③ 通过 update 钩子,可以监听指令值的变化,进行dom更新操作
自定义指令 - v-loading 指令的封装
1.场景:
实际开发过程中,发送请求需要时间,在请求的数据未回来时,页面会处于空白状态 => 用户体验不好
2.需求:
封装一个 v-loading 指令,实现加载中的效果
3.分析:
1.本质 loading效果就是一个蒙层,盖在了盒子上
2.数据请求中,开启loading状态,添加蒙层
3.数据请求完毕,关闭loading状态,移除蒙层
4.实现:
1.准备一个 loading类,通过伪元素定位,设置宽高,实现蒙层
2.开启关闭 loading状态(添加移除蒙层),本质只需要添加移除类即可
3.结合自定义指令的语法进行封装复用
.loading:before {content: "";position: absolute;left: 0;top: 0;width: 100%;height: 100%;background: #fff url("./loading.gif") no-repeat center;
}
5.代码示例:
<template><div class="main"><div class="box" v-loading="isLoading"><ul><li v-for="item in list" :key="item.id" class="news"><div class="left"><div class="title">{{ item.title }}</div><div class="info"><span>{{ item.source }}</span><span>{{ item.time }}</span></div></div><div class="right"><img :src="item.img" alt=""></div></li></ul></div><div class="box2" v-loading="isLoading2"></div></div>
</template><script>
// 安装axios => yarn add axios
import axios from 'axios'// 接口地址:http://hmajax.itheima.net/api/news
// 请求方式:get
export default {data () {return {list: [],isLoading: true,isLoading2: true}},async created () {// 1. 发送请求获取数据const res = await axios.get('http://hmajax.itheima.net/api/news')setTimeout(() => {// 2. 更新到 list 中,用于页面渲染 v-forthis.list = res.data.datathis.isLoading = false}, 2000)},directives: {loading: {inserted (el, binding) {binding.value ? el.classList.add('loading') : el.classList.remove('loading')},update (el, binding) {binding.value ? el.classList.add('loading') : el.classList.remove('loading')}}}
}
</script><style>
.loading:before {content: '';position: absolute;left: 0;top: 0;width: 100%;height: 100%;background: #fff url('./loading.gif') no-repeat center;
}.box2 {width: 400px;height: 400px;border: 2px solid #000;position: relative;
}.box {width: 800px;min-height: 500px;border: 3px solid orange;border-radius: 5px;position: relative;
}
.news {display: flex;height: 120px;width: 600px;margin: 0 auto;padding: 20px 0;cursor: pointer;
}
.news .left {flex: 1;display: flex;flex-direction: column;justify-content: space-between;padding-right: 10px;
}
.news .left .title {font-size: 20px;
}
.news .left .info {color: #999999;
}
.news .left .info span {margin-right: 20px;
}
.news .right {width: 160px;height: 120px;
}
.news .right img {width: 100%;height: 100%;object-fit: cover;
}
</style>
📜总结:
1.通过指令相关语法,封装了指令 v-loading 实现了请求的 loading 效果
2.核心思路:
(1)准备类名 loading,通过伪元素提供遮罩层
(2)添加或移除类名,实现loading蒙层的添加移除
(3)利用指令语法,封装 v-loading 通用指令
- inserted 钩子中,binding.value 判断指令的值,设置默认状态
- update 钩子中,binding.value 判断指令的值,更新类名状态
二、①插槽-默认插槽
1.作用:
让组件内部的一些 结构 支持 自定义
2.需求:
将需要多次显示的对话框,封装成一个组件
3.问题:
组件的内容部分,不希望写死,希望能使用的时候自定义。怎么办??
4.插槽的基本语法:
- 组件内需要定制的结构部分,改用<slot></slot>占位
- 使用组件时, <MyDialog></MyDialog>标签内部, 传入结构替换slot
- 给插槽传入内容时,可以传入纯文本、HTML标签、组件
5.代码示例:
MyDialog.vue
<template><div class="dialog"><div class="dialog-header"><h3>友情提示</h3><span class="close">✖️</span></div><div class="dialog-content"><!-- 1. 在需要定制的位置,使用slot占位 --><slot></slot></div><div class="dialog-footer"><button>取消</button><button>确认</button></div></div>
</template><script>
export default {data () {return {}}
}
</script><style scoped>
* {margin: 0;padding: 0;
}
.dialog {width: 470px;height: 230px;padding: 0 25px;background-color: #ffffff;margin: 40px auto;border-radius: 5px;
}
.dialog-header {height: 70px;line-height: 70px;font-size: 20px;border-bottom: 1px solid #ccc;position: relative;
}
.dialog-header .close {position: absolute;right: 0px;top: 0px;cursor: pointer;
}
.dialog-content {height: 80px;font-size: 18px;padding: 15px 0;
}
.dialog-footer {display: flex;justify-content: flex-end;
}
.dialog-footer button {width: 65px;height: 35px;background-color: #ffffff;border: 1px solid #e1e3e9;cursor: pointer;outline: none;margin-left: 10px;border-radius: 3px;
}
.dialog-footer button:last-child {background-color: #007acc;color: #fff;
}
</style>
App.vue
<template><div><!-- 2. 在使用组件时,组件标签内填入内容 --><MyDialog><div>你确认要删除么</div></MyDialog><MyDialog><p>你确认要退出么</p></MyDialog></div>
</template><script>
import MyDialog from './components/MyDialog.vue'
export default {data () {return {}},components: {MyDialog}
}
</script><style>
body {background-color: #b3b3b3;
}
</style>
📜总结:
场景:组件内某一部分结构不确定,想要自定义怎么办
使用:插槽的步骤分为哪几步?
场景: 当组件内某一部分结构不确定,想要自定义怎么办?
用插槽 slot占位封装
使用: 插槽使用的基本步骤?
1.先在组件内用 slot占位
2.使用组件时,传入具体标签内容插入
②插槽-后备内容(默认值)
1.问题:
通过插槽完成了内容的定制,传什么显示什么, 但是如果不传,则是空白
能否给插槽设置 默认显示内容 呢?
2.插槽的后备内容:
封装组件时,可以为预留的`<slot>`
插槽提供后备内容(默认内容)。
3.语法:
在<slot> </slot> 标签内,放置内容, 作为默认显示内容
4.效果: