前端面试

vue2.0传值方法的归纳

2018-04-24  本文已影响619人  gesila

使用vue2.0做过几个项目,传值,最初只会emit的方法,导致整个项目都是emit,而且项目没有合理的划分,有些写成父子形式,传递是很方便的,而且整个项目逻辑也很清晰。

1.同辈组件传值,使用emit和on

<!DOCTYPE html>
<html>
    <head>
        <meta charset="UTF-8">
        <title></title>
    </head>
    <body>
        <div id="app">
            <v-hello></v-hello>
            <v-hi></v-hi>
        </div>
        <template id="vHello">
            <div>{{getData}}</div>
        </template>
        <template id="vHi">
            <button @click='chuan'>传值</button>
        </template>
    </body>
    <script src="vue.js"></script>
    <script>
        var newEvent = new Vue();
        Vue.component('v-hello',{
            template: '#vHello',
             data(){
                return{
                    getData:'无'
                }
            },
            mounted(){
                var that =this;
                newEvent.$on('res',function(data){
                    that.getData=data;
                })
            }
        });
        Vue.component('v-hi',{
            template: '#vHi',
            methods:{
                chuan(){
                    newEvent.$emit("res",'我收到啦')
                }
            }
        })
        new Vue({
            el: '#app',   
        })

    </script>
</html>

在这里我注册了两个同等级的组件,传值时候需要在全局的情况下,不能用this.$emit,所以我在这里var了一个全局的vue。
如果是在vue+webpack的架构下传值,一般我会先写一个eventBus.js,new一个全局的vue

import Vue from 'vue'
export default new Vue;

传值的时候,在需要使用的组件下导入

import bus from 'assets/eventBus';

使用方法:

bus.$emit("res",'我收到啦');
bus.$on('res',function(data){
          that.getData=data;
})

2.父子间传递,使用props

<!DOCTYPE html>
<html>
    <head>
        <meta charset="UTF-8">
        <title></title>
    </head>
    <body>
        <div id="app">
            <v-hello :name='res'></v-hello>
        </div>
        <template id="vHello">
            <div>{{getData}}</div>
        </template>
    </body>
    <script src="vue.js"></script>
    <script>
        var newEvent = new Vue();
        Vue.component('v-hello',{
            template: '#vHello',
             data(){
                return{
                    getData:'无'
                }
            },
            props:['name'],
            mounted(){
                var that =this;
                that.getData=that.name;
            }
        });
        new Vue({
            el: '#app',
            data(){
                return{
                    res:'这是父传的值'
                }
            }   
        })

    </script>
</html>

如果你想写一个点击事件,点击父然后传递给子元素,我觉得你可以在子元素写一个监听事件,监听值的实时变化

 Vue.component('v-hello',{
            template: '#vHello',
            props:['name'],
             data(){
                return{
                    getData:'无'
                }
            },
            watch:{
                 name(){
                      return this.name;
                 }
            },
            mounted(){
                var that =this;
                that.getData=that.name;
            }
        });

要注意的是,props是父传递给子,子传递给父的时候得使用第一种emit的方法传递。

3.使用路由传递值(底下这个例子是在vue+webpack的架构下传值的方法)

3.1params传值

第一步:路由配置:这种写法是需要在url显示,:name就是要传递的参数


router.png

第二步:父组件:这里我需要的数据比较多,所以通过params传递的值多,但是显示在url的只有name


index.png
如果不写router-link,点击跳转传值这里也可以这么写
this.$router.push({
         name: `video`,
         params:{
              name:name
         }
})

第三步:子组件


child.png

3.2query传值

注意:query传递的参数会显示在url后面?name=
路由配置

{
      path: '/shipin',
      name:'shipin',
      component: shipin,
      children:[
        {name:'shipin',path:'/shipin',component:mainVideo},
        {name:'video',path:'/shipin/video',component:singleVideo}
      ]
    },

父组件

this.$router.push({
         name: `video`,
         query:{
              name:name
         }
})

子组件

this.$route.query

4.使用vuex传值

犹豫平时做的项目的类别,基本没有用过vuex,个人认为vuex比较适合大型复杂的项目,多个组件之间传递状态,组件之类,例如登录,购物车等功能就挺适合的,有啥问题请多提出,这里不熟,先简单的说一下,后面等总结好了,再归纳
接下来这个例子我说一个简答的Loading功能:
建立一个vuex文件夹,里面包括的文件有


image.png

在main.js引用

import store from './vuex/store'
new Vue({
  el: '#app',
  router,
  store,
  template: '<App/>',
})

state.js Vuex store 实例的根 state 对象,这里当做state的最初对象

export default {
  // 页面是否在加载中
  isLoading: true
}

getters.js 这里我就当做获取loading状态

export default {
  // 得到是否加载中
  getloading: (state) => state.isLoading,
}

mutations.js 改变状态,处理数据,这里就是改变loading的状态

export default {
  // 设置是否在加载
  SET_LOADING (state, platform) {
    state.isLoading = platform
  },
}

actions.js 异步处理,通过mutations改变状态

export default {
  // 改变是否正在加载状态
  setLoading ({commit}, platform) {
    commit('SET_LOADING', platform)
  },
}

store.js

import Vue from 'vue'
import Vuex from 'vuex'
import state from './state'
import mutations from './mutations'
import getters from './getters'
import actions from './actions'
Vue.use(Vuex)
export default new Vuex.Store({
  state,
  mutations,
  getters,
  actions
})

把loading放在主页,app.vue,项目打开的时候出现Loading

<template>
  <div id="app">
     <transition name="router-fade" mode="out-in">
      <router-view></router-view>
    </transition>
    <!--是否显示加载图标,在首页根据渲染是否完成加载-->
    <div class="loading_jump" v-if="isLoading">
      <div class="loading_jump1"></div>
      <div class="loading_jump2"></div>
    </div>
  </div>
</template>
<script>
  export default {
    name: 'app',
    computed: {
      isLoading () {
        return this.$store.getters.getloading
      }
    },
      mounted(){
      }
  }
</script>

当页面加载完成之后,关闭loading

this.$store.dispatch('setLoading', false)

总结:后面的写的不咋地,以后会慢慢修改的,谢谢

上一篇 下一篇

猜你喜欢

热点阅读