❤ 作者主页:欢迎来到我的技术博客
❀ 个人介绍:大家好,本人热衷于Java后端开发,欢迎来交流学习哦!( ̄▽ ̄)~*
如果文章对您有帮助,记得关注、点赞、收藏、评论⭐️⭐️⭐️
您的支持将是我创作的动力,让我们一起加油进步吧!!!
当应用中的 js 都以模块来编写的, 那这个应用就是一个模块化的应用。
当应用中的功能都是多组件的方式来编写的, 那这个应用就是一个组件化的应用。
代码:
基本使用
{{msg}}
总结:
Vue中使用组件的三大步骤:
如何定义一个组件:?
使用 Vue.extend(options)
创建,其中 options
和 new Vue(options)
时传入的那个 options
几乎一样,但也有点区别:
备注:使用template可以配置组件结构。
如何注册组件?
new Vue
的时候传入 components
选项Vue.component('组件名',组件)
编写组件标签:
例如:
代码:
几个注意点
{{msg}}
总结:
几个注意点:
关于组件名
一个单词组成:
多个单词组成:
备注:
关于组件标签
会导致后续组件不能渲染。一个简写方式
const school = Vue.extend(options)
可简写为:const school = options
代码:
组件的嵌套
效果:
代码:
VueComponent
总结:
关于 VueComponent
:
school组件本质是一个名为 VueComponent
的构造函数,且不是程序员定义的,是 Vue.extend
生成的。
我们只需要写
或
,Vue解析时会帮我们创建school组件的实例对象,即Vue帮我们执行的:new VueComponent(options)
。
特别注意:每次调用 Vue.extend
,返回的都是一个全新的VueComponent
。
关于this指向:
new Vue(options)
配置中:data函数、methods中的函数、watch中的函数、computed中的函数 它们的this均是【Vue实例对象】。VueComponent
的实例对象,以后简称vc(也可称之为:组件实例对象)。
代码:
一个重要的内置关系
总结:
VueComponent.prototype.__proto__ === Vue.prototype
School.vue
学校名称:{{name}}
学校地址:{{address}}
Student.vue:
学生姓名:{{name}}
学生年龄:{{age}}
App.vue
main.js
import App from './App.vue'
new Vue({
template:` `,
el:'#root',
components:{App}
})
index.html
单文件组件练习
npm config set registry http://registry.npm.taobao.org
npm install -g @vue/cli
vue create xxxx
npm run serve
Ctrl+C
备注:
Vue 脚手架隐藏了所有 webpack 相关的配置,若想查看具体的 webpakc 配置,请执行:vue inspect > output.js
脚手架文件结构:
.文件目录
├── node_modules
├── public
│ ├── favicon.ico: 页签图标
│ └── index.html: 主页面
├── src
│ ├── assets: 存放静态资源
│ │ └── logo.png
│ │── component: 存放组件
│ │ └── HelloWorld.vue
│ │── App.vue: 汇总所有组件
│ └── main.js: 入口文件
├── .gitignore: git版本管制忽略的配置
├── babel.config.js: babel的配置文件
├── package.json: 应用包配置文件
├── README.md: 应用描述文件
└── package-lock.json: 包版本控制文件
import Vue from 'vue'
import App from './App.vue'
Vue.config.productionTip = false
new Vue({
el:'#app',
// 简写形式
render: h => h(App),
// 完整形式
// render(createElement){
// return createElement(App)
// }
})
总结:
关于不同版本的函数:
vue.js
与 vue.runtime.xxx.js
的区别:
vue.js
是完整版的 Vue,包含:核心功能+模板解析器vue.runtime.xxx.js
是运行版的 Vue,只包含核心功能,没有模板解析器因为 vue.runtime.xxx.js
没有模板解析器,所以不能使用 template
配置项,需要使用 render
函数接收到的 createElement
函数去指定具体内容
vue.config.js
是一个可选的配置文件,如果项目的(和 package.json
同级的)根目录中存在这个文件,那么它会被 @vue/cli-service
自动加载vue.config.js
可以对脚手架进行个性化定制,详情见:https://cli.vuejs.org/zhmodule.exports = {
pages: {
index: {
// 入口
entry: 'src/index/main.js'
}
},
// 关闭语法检查
lineOnSave:false
}
代码:
School.vue
学校名称:{{name}}
学校地址:{{address}}
App.vue
总结:
ref
属性:
document.getElementById()
).....
或
this.$refs.xxx
代码:
Student.vue
{{msg}}
学生姓名:{{name}}
学生性别:{{sex}}
学生年龄:{{myAge+1}}
App.vue
总结:
props配置项:
功能:让组件接收外部传过来的数据
传递数据:
接收数据:
第一种方式(只接收):props:['name']
第二种方式(限制类型):props:{name:String}
第三种方式(限制类型、限制必要性、指定默认值):
props:{
name:{
type:String, //类型
required:true, //必要性
default:'老王' //默认值
}
}
备注:props是只读的,Vue底层会监测你对props的修改,如果进行了修改,就会发出警告,若业务需求确实需要修改,那么请复制props的内容到data中一份,然后去修改data中的数据。
1. 局部混入
代码:
School.vue
学校名称:{{name}}
学校地址:{{address}}
Student.vue
学生姓名:{{name}}
学生性别:{{sex}}
mixin.js
export const hunhe = {
methods: {
showName(){
alert(this.name)
}
},
mounted() {
console.log('你好啊!')
},
}
export const hunhe2 = {
data() {
return {
x:100,
y:200
}
},
}
2. 全局混入
代码:
School.vue
学校名称:{{name}}
学校地址:{{address}}
Student.vue
学生姓名:{{name}}
学生性别:{{sex}}
main.js
//引入Vue
import Vue from 'vue'
//引入App
import App from './App.vue'
import {hunhe,hunhe2} from './mixin'
//关闭Vue的生产提示
Vue.config.productionTip = false
Vue.mixin(hunhe)
Vue.mixin(hunhe2)
//创建vm
new Vue({
el:'#app',
render: h => h(App)
})
总结:
功能:可以把多个组件共用的配置提取成一个混入对象,实现组件功能的复用。
使用方式:
第一步定义混合:
export const xxx = {
data() {
},
methods: {
}
....
}
第二步使用混入:
全局混入:Vue.mixin(xxx)
局部混入:mixins:['xxx']
mixin的优点:
注意事项:
src/components/School.vue
学校名称:{{name | mySlice}}
学校地址:{{address}}
src/components/Student.vue
学生姓名:{{name}}
学生性别:{{sex}}
src/plugin.js
export default {
install(Vue,x,y,z){
console.log(x,y,z)
//全局过滤器
Vue.filter('mySlice',function(value){
return value.slice(0,4)
})
//定义全局指令
Vue.directive('fbind',{
//指令与元素成功绑定时(一上来)
bind(element,binding){
element.value = binding.value
},
//指令所在元素被插入页面时
inserted(element,binding){
element.focus()
},
//指令所在的模板被重新解析时
update(element,binding){
element.value = binding.value
}
})
//定义混入
Vue.mixin({
data() {
return {
x:100,
y:200
}
},
})
//给Vue原型上添加一个方法(vm和vc就都能用了)
Vue.prototype.hello = ()=>{alert('你好啊')}
}
}
src/main.js
//引入Vue
import Vue from 'vue'
//引入App
import App from './App.vue'
//引入插件
import plugins from './plugins'
//关闭Vue的生产提示
Vue.config.productionTip = false
//应用(使用)插件
Vue.use(plugins,1,2,3)
//创建vm
new Vue({
el:'#app',
render: h => h(App)
})
总结:
功能:用于增强Vue
本质:包含install方法的一个对象,install的第一个参数是Vue,第二个以后的参数是插件使用者传递的数据。
定义插件:
对象.install = function (Vue, options) {
// 1. 添加全局过滤器
Vue.filter(....)
// 2. 添加全局指令
Vue.directive(....)
// 3. 配置全局混入(合)
Vue.mixin(....)
// 4. 添加实例方法
Vue.prototype.$myMethod = function () {...}
Vue.prototype.$myProperty = xxxx
}
使用插件:Vue.use()
src/components/Student.vue
学校名称:{{name}}
学校地址:{{address}}
src/components/School.vue
学生姓名:{{name}}
学生性别:{{sex}}
App.vue
你好啊
总结:
在传统的CSS中,样式规则是全局的,会对整个页面中所有匹配的元素生效。这可能导致样式冲突和命名空间污染的问题。
为了解决这些问题,HTML5中引入了 scoped
样式。当在 标签中添加
scoped
属性时,样式规则只会应用于当前组件或元素及其子元素,而不会泄漏到其他组件或元素中。
scoped
样式是一种用于指定样式仅应用于当前组件或元素的CSS样式作用域。
注意: scoped
样式一般不会在 App.vue
中使用。
src/components/MyHeader.vue
src/components/MyList.vue
src/components/MyItem.vue
-
src/components/MyFooter.vue
src/App.vue
总结:
组件化编码流程:
(1)拆分静态组件:组件要按照 功能 点拆分,命名不要与html元素冲突。
(2)实现动态组件:考虑好数据的存放位置,数据是一个组件在用,还是一些组件在用:
(1)一个组件在用:放在组件自身即可。
(2)一些组件在用:放在他们共同的父组件上(状态提升)。
(3)实现交互:从绑定事件开始。
props
适用于:
(1)父组件 ==> 子组件 通信
(2)子组件 ==> 父组件 通信(要求父先给子一个函数)
使用 v-model
时要切记:v-model
绑定的值不能是 props
传过来的值,因为 props
是不可以修改的!
props
传过来的若是对象类型的值,修改对象中的属性时 Vue
不会报错,但不推荐这样做。
代码:
localStorage.html
localStorage
localStorage
sessionStorage.html
sessionStorage
sessionStorage
总结:
存储内容大小一般支持5MB左右(不同浏览器可能不一样)
浏览器端通过 Window.sessionStorage
和 Window.localStorage
属性来实现本地存储机制。
相关API:
xxxxxStorage.setItem('key', 'value')
该方法接受一个键和值作为参数,会把键值对添加到存储中,如果键名存在,则更新其对应的值。
xxxxxStorage.getItem('person')
该方法接受一个键名作为参数,返回键名对应的值。
xxxxxStorage.removeItem('key')
该方法接受一个键名作为参数,并把该键名从存储中删除。
xxxxxStorage.clear()
该方法会清空存储中的所有数据。
备注:
SessionStorage
存储的内容会随着浏览器窗口关闭而消失。LocalStorage
存储的数据是持久性的,可以长时间保存,需要手动清除才会消失。xxxxxStorage.getItem(xxx)
如果xxx对应的value获取不到,那么 getItem()
的返回值是null。JSON.parse(null)
的结果依然是null。src/App.vue
src/App.vue
src/components/School.vue
学校名称:{{name}}
学校地址:{{address}}
src/components/Student.vue
学生姓名:{{name}}
学生性别:{{sex}}
src/App.vue
src/components/Student.vue
学生姓名:{{name}}
学生性别:{{sex}}
总结:
一种组件间通信的方式,适用于:子组件 ===> 父组件
使用场景:A是父组件,B是子组件,B想给A传数据,那么就要在A中给B绑定自定义事件(事件的回调在A中)。
绑定自定义事件:
第一种方式,在父组件中:
或
第二种方式,在父组件中:
<Demo ref="demo"/>
......
mounted(){
this.$refs.xxx.$on('custom-event',this.test)
}
若想让自定义事件只能触发一次,可以使用once
修饰符,或$once
方法。
触发自定义事件:this.$emit('custom-event',数据)
解绑自定义事件this.$off('custom-event')
组件上也可以绑定原生DOM事件,需要使用native
修饰符。
注意:通过this.$refs.xxx.$on('custom-event',回调)
绑定自定义事件时,回调要么配置在methods中,要么用箭头函数,否则this指向会出问题!
src/App.vue
src/components/MyHeader.vue
src/components/MyFooter
src/main.js
//引入Vue
import Vue from 'vue'
//引入App
import App from './App.vue'
//关闭Vue的生产提示
Vue.config.productionTip = false
//创建vm
new Vue({
el:'#app',
render: h => h(App),
beforeCreate() {
Vue.prototype.$bus = this //安装全局事件总线,$bus就是当前应用的vm
},
})
src/App.vue
{{msg}}
src/components/School.vue
学校名称:{{name}}
学校地址:{{address}}
src/components/Student.vue
学生姓名:{{name}}
学生性别:{{sex}}
总结:
一种组件间通信的方式,适用于 任意组件间通信。
安装全局事件总线:
new Vue({
......
beforeCreate() {
Vue.prototype.$bus = this //安装全局事件总线,$bus就是当前应用的vm
},
......
})
使用事件总线:
接收数据:A组件想接收数据,则在A组件中给$bus绑定自定义事件,事件的回调留在A组件自身。
methods(){
demo(data){......}
}
......
mounted() {
this.$bus.$on('xxxx',this.demo)
}
提供数据:this.$bus.$emit('xxxx',数据)
最好在 beforeDestroy
钩子中,用$off去解绑当前组件所用到的事件。
src/mian.js
import Vue from 'vue'
import App from './App.vue'
Vue.config.productionTip = false
new Vue({
el:"#app",
render: h => h(App),
beforeCreate() {
Vue.prototype.$bus = this
}
})
src/components/App.vue
src/components/MyItem.vue
-
src/components/School.vue
学校名称:{{name}}
学校地址:{{address}}
src/components/Student.vue
学生姓名:{{name}}
学生性别:{{sex}}
总结:
一种组件间通信的方式,适用于 任意组件间通信。
使用步骤:
安装pubsub:npm i pubsub-js
引入: import pubsub from 'pubsub-js'
接收数据:A组件想接收数据,则在A组件中订阅消息,订阅的回调留在A组件自身。
methods(){
demo(data){......}
}
......
mounted() {
this.pid = pubsub.subscribe('xxx',this.demo) //订阅消息
}
提供数据:pubsub.publish('xxx',数据)
最好在 beforeDestroy
钩子中,用 PubSub.unsubscribe(pid)
去取消订阅。
src/App.vue
src/components/myItem.vue
-
this.$nextTick(回调函数)
作用:在插入、更新或移除 DOM元素时,在合适的时候给元素添加样式类名。
写法:
准备好样式:
v-enter
:进入的起点v-enter-active
:进入过程中v-enter-to
:进入的终点v-leave
:离开的起点v-leave-active
:离开过程中v-leave-to
:离开的终点使用
包裹要过度的元素,并配置name属性:
你好啊!
备注:若有多个元素需要过度,则需要使用:
,且每个元素都要指定key
值。
非常感谢您阅读到这里,如果这篇文章对您有帮助,希望能留下您的点赞 关注 分享 留言thanks!!!