vue 相关

1.vue v-for 循环一个数组,key值报错,但是数据是正常显示的

报错:

v-for使用key,需要在key前加上:key;
srcList是个数组,key值绑定不能是数据类型Object的item,应该绑定item对象下一个属性,这个属性不能重复出现,否则依旧会出现key值报错;你这里可以改成v-for="(item,index) in srcList" :key="index",index对象数组里的索引,不会重复出现,也就不会报错

 

2.计算属性 和 watch 的区别

计算属性是自动监听依赖值的变化,从而动态返回内容,监听是一个过程,在监听的值变化时,可以触发一个回调,并做一些事情

所以区别来源于用法,只是需要动态值,那就用计算属性需要知道值的改变后执行业务逻辑,才用 watch,用反或混用虽然可行,但都是不正确的用法

watch 用法: 例如有请求需要再也没初始化的时候就执行一次,然后监听他的变化,很多人这么写:

created(){
  this.fetchPostList()
},
watch: {
  searchInputValue(){
    this.fetchPostList()
  }
}

上面这种写法,我们完全可以如下写:

watch: {
  searchInputValue:{
    handler: 'fetchPostList',
immediate:
true } }

immediate:true代表如果在 wacth 里声明了之后,就会立即先去执行里面的handler方法,如果为 false就跟我们以前的效果一样,不会在绑定的时候就执行。

3.keep-alive

简单来说,就是把一个组件的编译缓存起来

 

4.router 与 route 的区别

$route对象表示当前的路由信息,包含了当前 URL 解析得到的信息。包含当前的路径,参数,query对象等。

 // 1.$route.path
      字符串,对应当前路由的路径,总是解析为绝对路径,如 "/foo/bar"// 2.$route.params
      一个 key/value 对象,包含了 动态片段 和 全匹配片段,
      如果没有路由参数,就是一个空对象。
 // 3.$route.query
      一个 key/value 对象,表示 URL 查询参数。
      例如,对于路径 /foo?user=1,则有 $route.query.user == 1,
      如果没有查询参数,则是个空对象。
 // 4.$route.hash
      当前路由的 hash 值 (不带 #) ,如果没有 hash 值,则为空字符串。锚点
 // 5.$route.fullPath
      完成解析后的 URL,包含查询参数和 hash 的完整路径。
 // 6.$route.matched**
      数组,包含当前匹配的路径中所包含的所有片段所对应的配置参数对象。
 // 7.$route.name    当前路径名字**
 // 8.$route.meta  路由元信息

$router对象是全局路由的实例,是router构造方法的实例。

路由实例方法:

1. $router.push()

// 字符串
      this.$router.push('home')
// 对象
      this.$router.push({ path: 'home' })
// 命名的路由
      this.$router.push({ name: 'user', params: { userId: 123 }})
// 带查询参数,变成 /register?plan=123
      this.$router.push({ path: 'register', query: { plan: '123' }})


// push方法其实和<router-link :to="...">是等同的。
// 注意:push方法的跳转会向 history 栈添加一个新的记录,当我们点击浏览器的返回按钮时可以看到之前的页面。

2. $router.go()

// 页面路由跳转 前进或者后退
this.$router.go(-1) // 后退

3. $router.replace()

//push方法会向 history 栈添加一个新的记录,而replace方法是替换当前的页面,不会向 history 栈添加一个新的记录

// 一般使用replace来做404页面
this.$router.replace('/')

// 配置路由时path有时候会加 '/' 有时候不加,以'/'开头的会被当作根路径,就不会一直嵌套之前的路径。

5.vue base64编码

// 项目根目录下安装
npm install --save js-base64

// 项目文件中引入
let Base64 = require('js-base64').Base64

// base64编码
Base64.encode('dankogai');  // ZGFua29nYWk=
// base64解码
Base64.decode('5bCP6aO85by-');  // 小飼弾

// base64加密后的内容,如果放到 url中传输,就会出现空格问题,即经过加密的字符串中如果有‘+’号,就会变成空格
encodeURIComponent(Base64.encode('dankogai'))

6.vue 实现消息的无缝滚动效果

<template>
<div id="box" @mouseover="pause" @mouseout="goon">
  <ul id="con1" ref="con1" :class="{anim:animate==true}">
    <li v-for='item in items'>{{item.name}}</li>
  </ul>
</div>
</template>

<script>
 
 export default {
data() {
 return {
   animate:false,
    timer: null,
   items:[  //消息列表对应的数组
     {name:"马云"},
     {name:"雷军"},
     {name:"王勤"}
   ]
 }
},
created(){
  setInterval(this.scroll,1000) // 在钩子函数中调用我在method 里面写的scroll()方法,注意此处不要忘记加this,我在这个位置掉了好几次坑,都是因为忘记写this。
},
methods: {
  play () {
    this.timer = setInterval(this.scroll, 2000)
  },
    pause () {
      clearInterval(this.timer)
    },
    goon () {
      this.timer = setInterval(this.scroll, this.val.scrollSpeed *     1000)
    },
  scroll(){
    let con1 = this.$refs.con1;
    con1.style.marginTop='-30px';
    this.animate=!this.animate;
    var that = this; // 在异步函数中会出现this的偏移问题,此处一定要先保存好this的指向
    setTimeout(function(){
        that.items.push(that.items[0]);
        that.items.shift();
        con1.style.marginTop='0px';
        that.animate=!that.animate;  // 这个地方如果不把animate 取反会出现消息回滚的现象,此时把ul 元素的过渡属性取消掉就可以完美实现无缝滚动的效果了
    },500)
  }
}
}
</script>
 
<style>
 
*{
  margin: 0 ;
  padding: 0;
}
#box{
   300px;
  height: 32px;
  line-height: 30px;
  overflow: hidden;
  padding-left: 30px;
  border: 1px solid black;
  transition: all 0.5s;
}
.anim{
  transition: all 0.5s;
}
#con1 li{
  list-style: none;
  line-height: 30px;
  height: 30px;
}
</style>

7.vue 项目结构启动原理

vue调用顺序: index.html → main.js → app.vue → index.js → components/组件

一般项目创建好后会有三个文件:index.html、main.js、app.vue

1、index.html :所有vue文件都是单页面形式开发,所有vue组件都是通过index.html进行渲染加载。

2、main.js:相当于

java的入口函数,控制初次启动vue项目要加载的组件

import Vue from 'vue' 引入vue

import App from './App' 引入App.vue文件

import router from './router' 引入一段路由配置

Vue.use(C)全局方法定义为C

el:'#app'这个和index.html中的app组件挂钩。官网解释为:模板将会替换挂载的元素。

watch:用来监听路由的变换,可以用来定义页面切换时的过渡效果。

3、App.vue默认为一个根组件

export 中的name属性组件名字

created:生命周期函数

4、index.js文件

引入组件的代码

routes定义时,path为你以后页面间路由跳转的路径

name为import进来的名字

component也为这个名字

其他文件:

-build

-build.js 生产环境构建脚本

-utils.js 构建相关工具方法

-webpack.base.conf.js webpack基础配置

-webpack.dev.conf.js webpack开发环境配置

-webpack.prod.conf.js 生产环境配置

-confg 项目配置

--dev.env.js 开发环境变量

--index.js 项目配置文件

--prod.env.js 生产环境变量

--test.env.js 测试环境变量

-package.json npm包配置文件,里面定义了项目的npm脚本,依赖包等信息

-src 源码目录

--main.js 入口js文件

--app.vue 根组件

--components 公共组件目录

--title.vue


————————————————
版权声明:本文为CSDN博主「No Silver Bullet」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/sunhuaqiang1/article/details/85099769

8.vue 生命周期相关

生命周期:Vue 实例从开始创建、初始化数据、编译模板、挂载Dom→渲染、更新→渲染、卸载等一系列过程,我们称这是 Vue 的生命周期,各个阶段有相对应的事件钩子

注意:

  1. created阶段的ajax请求与mounted请求的区别:前者页面视图未出现,如果请求信息过多,页面会长时间处于白屏状态

  2. mounted 不会承诺所有的子组件也都一起被挂载。如果你希望等到整个视图都渲染完毕,可以用 vm.$nextTick

vue2.0之后主动调用$destroy()不会移除dom节点,作者不推荐直接destroy这种做法,如果实在需要这样用可以在这个生命周期钩子中手动移除dom节点

单个组件的生命周期

  1. 初始化组件时,仅执行了beforeCreate/Created/beforeMount/mounted四个钩子函数

  2. 当改变data中定义的变量(响应式变量)时,会执行beforeUpdate/updated钩子函数

  3. 当切换组件(当前组件未缓存)时,会执行beforeDestory/destroyed钩子函数

  4. 初始化和销毁时的生命钩子函数均只会执行一次,beforeUpdate/updated可多次执行

父子组件的生命周期

//父组件
<script>
import Child from './Child';
export default {
  components: {
    Child
  },
  beforeCreate() {
    console.log('parent before create');
  },
  created() {
    console.log('parent created');
  },
  beforeMount() {
    console.log('parent before mount');
  },
  mounted() {
    console.log('parent mounted')
  },
  render(h) {
    console.log('parent render');
    return (
      <div>
        <h1>Vue中父子组件的挂载顺序</h1>
        <h1>父亲</h1>
        <Child/>
      </div>
    )
  },
}
</script>

// 子组件
<script>
export default {
  beforeCreate() {
    console.log('child before create');
  },
  created() {
    console.log('child created');
  },
  beforeMount() {
    console.log('child before mount');
  },
  mounted() {
    console.log('child mounted')
  },
  render(h) {
    console.log('child render');
    return (
      <div>
        <h1>Vue中父子组件的挂载顺序</h1>
        <h1>孩子</h1>
      </div>
    )
  },
}
</script>

父子组件中使用render函数代替<template>,打印输出结果

 父组件先初始化 -> 父组件渲染完毕 -> 子组件开始初始化 -> 子组件挂载完毕 -> 父组件挂载完毕

  1. 仅当子组件完成挂载后,父组件才会挂载

  2. 当子组件完成挂载后,父组件会主动执行一次beforeUpdate/updated钩子函数(仅首次)

  3. 父子组件在data变化中是分别监控的,但是在更新props中的数据是关联的(可实践)

  4. 销毁父组件时,先将子组件销毁后才会销毁父组件

兄弟组件的生命周期

  1. 组件的初始化(mounted之前)分开进行,挂载是从上到下依次进行

  2. 当没有数据关联时,兄弟组件之间的更新和销毁是互不关联的

宏mixin的生命周期

  1. mixin中的生命周期与引入该组件的生命周期是仅仅关联的,且mixin的生命周期优先执行

9. 怎样监听vuex中的数据变化

将vuex中的数据映射成组件中的计算属性

import { mayState } from 'vuex';
.
.
.
computed: {
  ...mapState([ 'dataName' ])  
}

10. 自定义组件的v-model

// 父组件
<template>
  <div class="login">
   <BaseInput :value="message" @input="message = $event"/> 
  <p>文字: {{message}}</p>
  <hr/>
  <BaseCheckbox style="40px;height:40px;" :checked="checked" @change="checked = $event"></BaseCheckbox>
  <p>是否选中: {{checked}}</p> </div> </template> <script>

import BaseInput from "./baseInput" import BaseCheckbox from './baseCheckbox' export default { components: {
  BaseInput, BaseCheckbox }, data() {
return {
    message: 'Hello 输入框', checked:
true, } } }; </script>
// 子组件baseCheckbox
<template>
  <div>
    <input type="checkbox" :checked="checked" @change="handleChange" />
  </div>
</template>

<script>
export default {
  model: {
    prop: 'checked',
    event: 'change'
  },
  props: ['checked'],
  methods: {
    handleChange(e) {
      this.$emit('change', e.target.checked);
    }
  }
};
</script>
// 子组件baseInput
<template>
  <div>
    <input type="text" :value="value" @input="handleInput" />
  </div>
</template>

<script>
export default {
  props: ['value'],
  methods: {
    handleInput(e) {
      this.$emit('input', e.target.value);
    }
  }
};
</script>

11. Vue异步组件

在项目当中有些组件不想马上加载,如点击按钮之后再加载组件,可以使用异步组件

<template>
  <div>
    <h1>vue异步组件的使用</h1>
    <button @click="handleClick">点击加载组件</button>
    <div v-if="show">
      <List />
    </div>
  </div>
</template>

<script>
export default {
  components: {
    // 使用异步组件,在需要的时候发送ajax请求,下载对应组件的代码
    // List: ()=> import('./list')
    // 为了便于查看,在控制台中设置文件名称为 list
    List: ()=> import(/* webpackChunkName: list */'./baseCheckbox')
  },
  data() {
    return {
      show: false
    }
  },
  methods: {
    handleClick() {
      this.show = !this.show;
    }
  }
}
</script>

或者使用异步组件工厂函数的形式,设置加载属性,如加载时间,延时时间,加载失败后组件等等

<template>  
 <div>
  <h1>vue异步组件的使用</h1> <button @click="handleClick">点击加载组件</button> <div v-if="show"> <AsyncList/> </div> </div> </template> <script> import LoadingComponent from './LoadingComponent';
import ErrorComponent from './ErrorComponent';
const AsyncList = () => {
  return {
    component: import('./list'),
    loading: LoadingComponent,
    error: ErrorComponent,
    delay: 200,
    timeout: 3000
  }
} export
default { components: { AsyncList }, data() { return { show: false } }, methods: { handleClick() { this.show = !this.show; } } } </script>
原文地址:https://www.cnblogs.com/lingnweb/p/10606325.html