Vue2学习之路(2):组件通信&&代理配置&&Vuex

上一篇:Vue2学习之路(1):Vue基础知识和组件化

vue

主要是父子组件通信(祖孙组件通信必须利用父组件进行props间接配置,或者使用v-model)

<!-- MyList.vue -->
<template>
	<ul>
	<!-- 此处:todop='p'相当于指定了子组件的对象 -->
	<MyItem v-for='p in arr' :key='p.id' :todop='p'/>
    </ul>
</template>
<script type='text/javascript'>
	export default {
      
      
        name: 'MyList',
        components: {
      
      MyItem},
        data() {
      
      
            return {
      
      
                arr: {
      
      
                    {
      
      id: '001', name: '1'},
                	{
      
      id: '002', name: '2'},
                    {
      
      id: '003', name: '3'},
                }
            }
        }
    }
</script>
<!-- MyItem.vue -->
<template>
	<li>
    	<label>
    		<input type='checkbox' :check='todop.done'/>
            <span> {
   
   { todo.name }} </span>
    	</label>
    </li>
</template>
<script>
    export default {
      
      
        name: 'MyItem',
        props: [
            // 声明接收todop对象,数据是动态的
            'todop',
        ]
    }
</script>

小技巧:将一个数据放到data中的arr中,this.arr.unshift(x)

数据在哪里,操作数据的方法在哪里

浏览器本地存储

js原生

localStorage:类似于cookies

<!-- localStorage是浏览器本地信息存储(不是session) -->
<script>
    // 存储
	function saveData() {
      
      
        localStorage.setItem('key', 'value')
    }
    // read
	function readData() {
      
      
        localStorage.getItem('key')
    }
    // delete
	function deleteData() {
      
      
        localStorage.removeItem('key', 'value')
    }
</script>

sessionStorage:关闭浏览器即消失

<!-- localStorage是浏览器本地信息存储(不是session) -->
<script>
    // 存储
	function saveData() {
      
      
        sessionStorage.setItem('key', 'value')
    }
    // read
	function readData() {
      
      
        sessionStorage.getItem('key')
    }
    // delete
	function deleteData() {
      
      
        sessionStorage.removeItem('key', 'value')
    }
</script>

组件自定义事件

主要是子父组件通信

<!-- list.vue -->
<div>
    <button @click="addsome">
        xxx
    </button>
</div>
<script>
	export default {
      
      
        // do something
        methods: {
      
      
            addsome() {
      
      
                // 触发list组件上的add事件
				this.$emit('add')
            }
        }
    }
</script>
<!-- app.vue -->
<div>
    <list v-on:add='addfu'/>
    <!-- <list @add='addfu'/> -->
</div>
<script>
	export default {
      
      
        // do something
        methods: {
      
      
            addfu() {
      
      
		   		
            }
        }
    }
</script>

解绑事件

<script>
	// do something
    methods: {
      
      
		unbind() {
      
      
            // 解绑一个自定义事件
		   this.$off('xxx')
            // 解绑所有的自定义事件
            this.$off(['a', 'b', 'c'])
            // 销毁了该组件的所有实例,此时该组件的所有的自定义都不奏效了
            this.$destroy()
        }
    }
</script>

全局事件总线

  • 所有的组件都能看到他(让组件实例对象(vc)可以访问到 Vue原型上的属性、方法。)
  • 调用$on
  • 调用$off
  • 调用$emit
<!-- main.js -->
Vue.prototype.x = {a:1, b:2}

算了,直接在main.js中改导致该文件太臃肿,略

消息订阅与发布

npm i pubsub-js

引入库

<!-- 发送者 -->
<script>
	import pubsub from 'pubsub-js'
    export default {
      
      
        // do something
        sendInfo() {
      
      
            pubsub.publish('hello', 'myname')
        }
    }
</script>
<!-- 接收者 -->
<script>
	import pubsub from 'pubsub-js'
    export default {
      
      
        // do something
        mounted() {
      
      
            // msg=hello为消息名
            this.pubid = pubsub.subscribe('hello', (msg, data)=> {
      
      
                // do something
            })
        },
        beforeDeatroy() {
      
      
            // 销毁消息
            pubsub.unsubscribe(this.pubid)
        }
    }
</script>

动画效果

不常用

<div>
    <transition>
    	<h1>
            Hello World
        </h1>
    </transition>
</div>

配置代理

npm i axios

这一点是和后端数据进行交互的

<!-- 代理配置 -->
module.exports = {
    
    
	pages: {
    
    
		index: {
    
    
			// 入口
			entry: 'src/main.js',
		},
	},
	lintOnSave:false,	// 关闭语法检查
    /* 方式一
	devServer: {
		proxy: 'http://localhost:5000',	// 代理server
	}*/
    // 方式二,针对不同的服务器
    devServer: {
    
    
        proxy: {
    
    
            'atguigu': {
    
    
                target: 'http://localhost:5000',
                pathRewrite: {
    
    '^atguigu': ''}	// 进行重定向
                ws: true, // websocket
                changeOrigin: false,	// host
            }
        }
    }
}

请求

<template>
	<div>
        <button @click="getInfo">
            
        </button>
    </div>
</template>
<script>
	import axios from 'axios'
    export default {
      
      
		name: 'app',
         methods: {
      
      
             // 反向代理
         	axios.get('url:8080/data').then(
        		response => {
      
      
        			// do something
    			},
    			error => {
      
      
        			// error
    			}
        	),   
         }
    }
</script>

Vuex

概念:专门在Vue中实现集中式状态(数据)管理的一个Vue插件,对vue应用中多个组件的共享状态进行集中式的管理(读/写),也是一种组件间通信的方式,且适用于任意组件间通信。

什么时候需要用

  • 多个组件依赖于同一状态-
  • 来自不同组件的行为需要变更同—状态

小tip:v-model.number强制转为数字

步骤:actions->mutations->state

vuefunction->actions

dispath('function', params)

actions->mutations

commit('function', params)

mutations->state

mutate()

state->vue

render()

搭建环境

npm i vuex
import Vuex from 'vuex'	// 导入库

Vue.use(Vuex)	// 使用插件

import store from 'store'	// 引入store

new Vue({
    
    
    el: '#app',
    render: h => h(app),
    store: store,
})
cd src
mkdir store
touch index.js
// 引入Vuex
import Vuex from 'vuex'

// actions-响应
const actions = {
    
    }
// mutations-操作数据
const mutations = {
    
    }
// state-存储数据
const state = {
    
    }

// 创建Store
export default new Vuex.Store({
    
    
    actions,
    mutations,
    state,
})

使用store

<h1>
    {
   
   { $store.state.sum }}
</h1>
<script>
	// do something
    methods: {
      
      
        add() {
      
      
            this.$store.dispatch('jia', this.n)
        }
    }
</script>
// index.js
const actions = {
    
    
    jia(context, value) {
    
    
        context.commit('mutfunc', value)
    }
}
const mutations = {
    
    
    mutfunc(state, value){
    
    
        state.sum += value
    }
}
const state = {
    
    
    sum: 0,
}

devtools中的mutation是怎么调用的

getters

const getters = {
    
    	// 用于将state中的数据进行加工
    bigSum(state) {
    
    
        return state.sum * 10
    }
}
export default new Vuex.Store({
    
    
    actions,
    mutations,
    state,
    getters,
})

怎么直接引用state的内容?

<script>
    import {
      
      mapState} from 'vuex'
    // do something
    computed: {
      
      
        // ...表示将其中的东西全部展开
        ...mapState({
      
      	// 只能生成state的关联
            sum: 'sum',
            name: 'name',
        }),	// 对象形式
    }
</script>

同理

<script>
	import {
      
      mapGetter} from 'vuex'
</script>
<script>
	import {
      
      mapActions} from 'vuex'
    methods: {
      
      
        ...mapActions([
            'func1',
            'func2'
        ])	// 数组形式
    }
</script>
<script>
	import {
      
      mapMutations} from 'vuex'
    methods: {
      
      
        ...mapMutations([
            'func1',
            'func2'
        ])
    }
</script>

模块化

对某些操作和数据放在一个命名空间(模块)

const countOptions = {
    
    	// 与人相关的
    namespaced: true,	// 开启命名空间
    actions: {
    
    },
    mutations: {
    
    },
    state: {
    
    },
    getters: {
    
    },
}
const countPerson = {
    
    	// 与人相关的
    namespaced: true,
    actions: {
    
    },
    mutations: {
    
    },
    state: {
    
    },
    getters: {
    
    },
}
export default new Vuex Store ({
    
    
    modules: {
    
    
        a: countOptions,
        b: countPerson,
    }
})

因此对于前面的也要改

<script>
    import {
      
      mapState} from 'vuex'
    // do something
    computed: {
      
      
        // 通过第一个参数来指定分类
        ...mapState('a', ['sum', 'name']),	
        ...mapState('b', ['person']),	
    }
</script>

猜你喜欢

转载自blog.csdn.net/qq_48322523/article/details/120878647