# vue-component
**Repository Path**: jsland/vue-component
## Basic Information
- **Project Name**: vue-component
- **Description**: 🅰️ write demos to study vue2's compontent deeply
- **Primary Language**: Unknown
- **License**: Not specified
- **Default Branch**: master
- **Homepage**: None
- **GVP Project**: No
## Statistics
- **Stars**: 0
- **Forks**: 0
- **Created**: 2021-06-30
- **Last Updated**: 2021-06-30
## Categories & Tags
**Categories**: Uncategorized
**Tags**: None
## README
# Vue组件
## 组件的主要特点
重用性 --能够公用和通用,因此在组件内部就不能写具体的业务逻辑
可定制性 --可设置参数和属性
高内聚性 --功能完整。组件资源内部高内聚,组件资源由自身加载控制
互操作性 --多组件协同工作
作用域独立 -- 内部结构密封,不与全局或其他组件产生影响
规范化接口 -- 组件接口有统一规范,或者是生命周期的管理
## 组件的API来自三部分
props参数 传递数据给组件
slot定制模板 外部模板混合子组件模板
event自定义事件 监控子组件交互状态
## 单向数据流
数据从父组件流向子组件,只能单向绑定。
在子组件内部不应该修改父组件传递过来的数据。 浏览器会报错。
解决的方法:
1. 作为data中局部数据的初始值使用
2. 作为子组件的computed属性
``` javascript
//错误示例
Vue.component('custom',{
props:['count'],
data(){
},
template:`
{{count}}
`,
methods:{
changeCount(){
this.count ++ //报错,不能直接修改从父组件传递过来的值
}
}
})
```
## props验证
根据配置来验证,如果不符合要求浏览器会有错误提示
``` javascript
props:{
count:{
type:Number, //类型,验证类型为原生构造器:String、Number、Function、Object、Boolean、Array
type:[Number,String],//多个类型验证
default:10, //默认值
required:true,//是否必填
validator:function(value){
return value > 10
} //自定义验证方式
}
}
```
## 使用slot分发内容
内容分发:使用一种方式混合父组件的内容和子组件自己的模板。
在子组件中使用特殊的作为内容的插槽,这样会使组件的可扩展性更强。
为什么不使用props传递数据?因为需要传递不同html结构的元素,父组件定制不同样子的模板,但props实现较为复杂
> 单个slot
父组件提供额外的内容,子组件会把整个内容片段插入slot所在Dom位置,并替换调slot标签。
> 具名slot
元素可以用一个特殊的属性name分配如何分发内容。同时可以使用一个匿名slot处理那些没有对应slot的内容。
> 作用域
父组件模板的内容在父组件作用域内编译;
子组件模板的内容在子组件作用域内编译
## 动态组件
多个组件可以使用同一个挂载点,动态在他们之间切换
使用``,使用is进行动态绑定
``` html
动态组件
//保存状态,不被改变
```
``` javascript
import cptOne from '@/components/cpt/cpt1'
import cptTwo from '@/components/cpt/cpt2'
import cptThree from '@/components/cpt/cpt3'
data () {
return {
curcomponet:cptOne
}
}
```
# 组件通信
https://github.com/Mirror198829/Vue2.X/issues/4
## 解析DOM模板时的注意事项
Vue是在浏览器解析和标准化html后才能获取模板内容,有些元素限制了被它包裹的元素。
例如:ul中只能放li,table里面只能放tbody;select中只能放option
通过`is`属性扩展原生html元素
# Vuex
参考地址:https://vuex.vuejs.org/zh/guide/
Vuex:状态管理模式,采用集中式存储管理应用的所有组件的状态,并以`相应的规则`(修改状态的唯一途径:mutation)保证状态以一种可预测的方式发生改变。
****
``` javascript
let store = new Vuex.Store({
state:{ //定义一个状态,状态的修改只能是提交mutations实现,无法直接赋值
count:110
},
mutations:{ //改变state状态,其中state是默认传的,通过commit触发
updateCount(state){
state.count += 1
}
},
getters:{ //数据深层次处理。类似组件的computed,是vuex对state的数据处理
totals(state){
return state.shopLst.reduce((startCount,item) => startCount+item.count,0)
}
},
actions:{ //异步操作,得通过分发方式出发 dispatch
updateCountAction(store,params){
setTimeout(() => {
store.commit('addNumAction',params)
},3000)
},
}
})
```
#### 核心概念
`store`:仓库,它包含大部分的状态,状态存储是响应式的,不能直接改变store中的状态
`getter`:派分状态,抽离操作状态的逻辑,可被多组件使用
`mutation`:mutation必须是同步更新状态;修改状态的唯一途径,要使改变状态可被记录,必须要commit一个mutation;如果mutation里面有异步的操作,那么记录的值还是之前的值。 因此,只要有异步操作就得放到action里面
`action`:异步操作,Action提交的是mutation,而不是直接变更状态,分发状态 dispatch
`modules`:应用变得非常复杂时,store 对象就有可能变得相当臃肿,因此Vuex 允许我们将 store 分割成模块(module)。每个模块拥有自己的 state、mutation、action、getter。
``` javascript
const moduleA = {
state: { ... },
mutations: { ... },
actions: { ... },
getters: { ... }
}
const moduleB = {
state: { ... },
mutations: { ... },
actions: { ... }
}
const store = new Vuex.Store({
modules: {
a: moduleA,
b: moduleB
}
})
store.state.a // -> moduleA 的状态
store.state.b // -> moduleB 的状态
```
>注意:
1. 传参通常传的是一个对象。
2. vuex中的状态是响应的,在data里面定义的不会因为state的改变而改变,只在当前组件有反应,所以要用计算属性才有反应。
#### vuex原则
1. 每个应用只有一个store实例
2. 更改store中的状态的唯一方法是提交mutation
3. mutation必须是同步函数
4. action可以包含任意异步操作
5. action提交的是mutation,而不是直接更改状态