vue2.0+vue3.0资料(尚硅谷)(四)

简介: vue2.0+vue3.0资料(尚硅谷)

3、ref属性

3-1、ref属性

  1. 被用来给元素或子组件注册引用信息(id的替代者)
  2. 应用在html标签上获取的是真实DOM元素,应用在组件标签上是组件实例对象(vc)
  3. 使用方式:
  1. 打标识:<h1 ref="xxx">.....</h1><School ref="xxx"></School>
  2. 获取:this.$refs.xxx

3-2、案例如下:

App.vue

<template>
  <div>
    <h1 v-text="msg" ref="title"></h1>
    <button ref="btn" @click="showDOM">点我输出上方的DOM元素</button>
    <School ref="sch"/>
  </div>
</template>
<script>
  //引入School组件
  import School from './components/School'
  export default {
    name:'App',
    components:{School},
    data() {
      return {
        msg:'欢迎学习Vue!'
      }
    },
    methods: {
      showDOM(){
        console.log(this.$refs.title) //真实DOM元素
        console.log(this.$refs.btn) //真实DOM元素
        console.log(this.$refs.sch) //School组件的实例对象(vc)
      }
    },
  }
</script>

4、props配置

4-1、props配置项

  1. 功能:让组件接收外部传过来的数据
  2. 传递数据:<Demo name="xxx"/>
  3. 接收数据:
  1. 第一种方式(只接收):props:['name']
  2. 第二种方式(限制类型):props:{name:String}
  3. 第三种方式(限制类型、限制必要性、指定默认值):
props:{
  name:{
  type:String, //类型
  required:true, //必要性
  default:'老王' //默认值
  }
}


备注:props是只读的,Vue底层会监测你对props的修改,如果进行了修改,就会发出警告,若业务需求确实需要修改,那么请复制props的内容到data中一份,然后去修改data中的数据。

4-2、案例如下

App.vue

<template>
  <div>
    <Student name="李四" sex="女" :age="18"/>
  </div>
</template>
<script>
  import Student from './components/Student'
  export default {
    name:'App',
    components:{Student}
  }
</script>

Student.vue

<template>
  <div>
    <h1>{{msg}}</h1>
    <h2>学生姓名:{{name}}</h2>
    <h2>学生性别:{{sex}}</h2>
    <h2>学生年龄:{{myAge+1}}</h2>
    <button @click="updateAge">尝试修改收到的年龄</button>
  </div>
</template>
<script>
  export default {
    name:'Student',
    data() {
      console.log(this)
      return {
        msg:'我是一个学生',
        myAge:this.age
      }
    },
    methods: {
      updateAge(){
        this.myAge++
      }
    },
    //简单声明接收
    // props:['name','age','sex'] 
    //接收的同时对数据进行类型限制
    /* props:{
      name:String,
      age:Number,
      sex:String
    } */
    //接收的同时对数据:进行类型限制+默认值的指定+必要性的限制
    props:{
      name:{
        type:String, //name的类型是字符串
        required:true, //name是必要的
      },
      age:{
        type:Number,
        default:99 //默认值
      },
      sex:{
        type:String,
        required:true
      }
    }
  }
</script>

5、mixin(混入)属性

5-1、mixin(混入)

  1. 功能:可以把多个组件共用的配置提取成一个混入对象
  2. 使用方式:
    第一步定义混合:
    {
    data(){....},
    methods:{....}
    ....
    }
    第二步使用混入:
    全局混入:Vue.mixin(xxx)
    局部混入:mixins:['xxx']

5-2、案例如下:

mix.js(这里定义了两个混入方法)

//定义了两个的方法
export const hunhe = {
  methods: {
    showName(){
      alert(this.name)
    }
  },
  mounted() {
    console.log('你好啊!')
  },
}
export const hunhe2 = {
  data() {
    return {
      x:100,
      y:200
    }
  },
}

main.js(这里是用了全局混入1和2)

//1、这里引入了两个混入属性在mixin.js中
import {hunhe,hunhe2} from './mixin'
//2、使用mixin.js中的两个混入效果
Vue.mixin(hunhe)
Vue.mixin(hunhe2)

Student.vue(1这里引入混入,2并使用了局部混入)

<template>
  <div>
    <h2 @click="showName">学生姓名:{{name}}</h2>
    <h2>学生性别:{{sex}}</h2>
  </div>
</template>
<script>
    //1、引入混入
  // import {hunhe,hunhe2} from '../mixin'
  export default {
    name:'Student',
    data() {
      return {
        name:'张三',
        sex:'男'
      }
    },
    
    //2、使用局部混入
    // mixins:[hunhe,hunhe2]
  }
</script>

6、插件

6-1、插件使用步骤

  1. 功能:用于增强Vue
  2. 本质:包含install方法的一个对象,install的第一个参数是Vue,第二个以后的参数是插件使用者传递的数据。
  3. 定义插件:
对象.install = function (Vue, options) {
    // 1. 添加全局过滤器
    Vue.filter(....)
    // 2. 添加全局指令
    Vue.directive(....)
    // 3. 配置全局混入(合)
    Vue.mixin(....)
    // 4. 添加实例方法
    Vue.prototype.$myMethod = function () {...}
    Vue.prototype.$myProperty = xxxx
}


  1. 使用插件:Vue.use()

6-2、案例如下:

plugins.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('你好啊')}
  }
}

main.js(引入并且使用插件的js)

//引入插件
import plugins from './plugins.js'
//应用(使用)插件
Vue.use(plugins,1,2,3)

School.vue(使用mySlice全局过滤器、使用Vue原型上的hello方法)

<template>
  <div>
    <h2>学校名称:{{name | mySlice}}</h2>
    <h2>学校地址:{{address}}</h2>
    <button @click="test">点我测试一个hello方法</button>
  </div>
</template>
<script>
  export default {
    name:'School',
    data() {
      return {
        name:'abcdefghighlim',
        address:'北京',
      }
    },
    methods: {
      test(){
        this.hello()
      }
    },
  }
</script>

Student.vue(使用fbind全局指令)

<template>
  <div>
    <h2>学生姓名:{{name}}</h2>
    <h2>学生性别:{{sex}}</h2>
    <input type="text" v-fbind:value="name">
  </div>
</template>
<script>
  export default {
    name:'Student',
    data() {
      return {
        name:'张三',
        sex:'男'
      }
    },
  }
</script>

7、scoped样式

7-1、scoped用法

  1. 作用:让样式在局部生效,防止冲突。
  2. 写法:<style scoped>

7-2、案例如下:

App.vue

<template>
  <div>
    <h1 class="title">你好啊</h1>
    <School/>
    <Student/>
  </div>
</template>
<script>
  import Student from './components/Student'
  import School from './components/School'
  export default {
    name:'App',
    components:{School,Student}
  }
</script>
<style scoped>
  .title{
    color: red;
  }
</style>

7-3、Todo-list案例

7-4、总结TodoList案例

1、组件化编码流程:

(1).拆分静态组件:组件要按照功能点拆分,命名不要与html元素冲突。

(2).实现动态组件:考虑好数据的存放位置,数据是一个组件在用,还是一些组件在用:

1).一个组件在用:放在组件自身即可。

2). 一些组件在用:放在他们共同的父组件上(状态提升)。

(3).实现交互:从绑定事件开始。

2、props适用于:
(1).父组件 ==> 子组件 通信
(2).子组件 ==> 父组件 通信(要求父先给子一个函数)
3、使用v-model时要切记:

v-model绑定的值不能是props传过来的值,因为props是不可以修改的!

4、修改props中的值的情况

props传过来的若是对象类型的值,修改对象中的属性时Vue不会报错,但不推荐这样做。

5、数据在哪里,操作数据就在哪里

关于表格中的删除效果和移动高亮

li:hover{
    background-color: #ddd;
  }
  
  li:hover button{
    display: block;
  }

reduce条件统计

//原来
let i=0
this.todos.foreach((todo))=>{
    if(todo.done) i++
}
//用reduce后
/* const x = this.todos.reduce((pre,current)=>{
          console.log('@',pre,current)
          return pre + (current.done ? 1 : 0)
        },0) */
//简写
        return this.todos.reduce((pre,todo)=> pre + (todo.done ? 1 : 0) ,0)

8、浏览器本地存储

8-1、webStorage

  1. 存储内容大小一般支持5MB左右(不同浏览器可能还不一样)
  2. 浏览器端通过 Window.sessionStorage 和 Window.localStorage 属性来实现本地存储机制。
  3. 相关API:
  1. xxxxxStorage.setItem('key', 'value');
    该方法接受一个键和值作为参数,会把键值对添加到存储中,如果键名存在,则更新其对应的值。
  2. xxxxxStorage.getItem('person');
    该方法接受一个键名作为参数,返回键名对应的值。
  3. xxxxxStorage.removeItem('key');
    该方法接受一个键名作为参数,并把该键名从存储中删除。
  4. xxxxxStorage.clear()
    该方法会清空存储中的所有数据。
  1. 备注:
  1. SessionStorage存储的内容会随着浏览器窗口关闭而消失。
  2. LocalStorage存储的内容,需要手动清除才会消失。
  3. xxxxxStorage.getItem(xxx)如果xxx对应的value获取不到,那么getItem的返回值是null。
  4. JSON.parse(null)的结果依然是null。

localStorage.html

<!DOCTYPE html>
<html>
  <head>
    <meta charset="UTF-8" />
    <title>localStorage</title>
  </head>
  <body>
    <h2>localStorage</h2>
    <button onclick="saveData()">点我保存一个数据</button>
    <button onclick="readData()">点我读取一个数据</button>
    <button onclick="deleteData()">点我删除一个数据</button>
    <button onclick="deleteAllData()">点我清空一个数据</button>
    <script type="text/javascript" >
      let p = {name:'张三',age:18}
      function saveData(){
        localStorage.setItem('msg','hello!!!')
        localStorage.setItem('msg2',666)
        localStorage.setItem('person',JSON.stringify(p))
      }
      function readData(){
        console.log(localStorage.getItem('msg'))
        console.log(localStorage.getItem('msg2'))
        const result = localStorage.getItem('person')
        console.log(JSON.parse(result))
        // console.log(localStorage.getItem('msg3'))
      }
      function deleteData(){
        localStorage.removeItem('msg2')
      }
      function deleteAllData(){
        localStorage.clear()
      }
    </script>
  </body>
</html>

sessionStorage.html

<!DOCTYPE html>
<html>
  <head>
    <meta charset="UTF-8" />
    <title>sessionStorage</title>
  </head>
  <body>
    <h2>sessionStorage</h2>
    <button onclick="saveData()">点我保存一个数据</button>
    <button onclick="readData()">点我读取一个数据</button>
    <button onclick="deleteData()">点我删除一个数据</button>
    <button onclick="deleteAllData()">点我清空一个数据</button>
    <script type="text/javascript" >
      let p = {name:'张三',age:18}
      function saveData(){
        sessionStorage.setItem('msg','hello!!!')
        sessionStorage.setItem('msg2',666)
        sessionStorage.setItem('person',JSON.stringify(p))
      }
      function readData(){
        console.log(sessionStorage.getItem('msg'))
        console.log(sessionStorage.getItem('msg2'))
        const result = sessionStorage.getItem('person')
        console.log(JSON.parse(result))
        // console.log(sessionStorage.getItem('msg3'))
      }
      function deleteData(){
        sessionStorage.removeItem('msg2')
      }
      function deleteAllData(){
        sessionStorage.clear()
      }
    </script>
  </body>
</html>

8-2、TodoList案例添加本地存储

把App.vue加一个监视属性并且设置它里面todos的初始值

//1设置todos初始值,将todos:[]改成
todos:JSON.parse(localStorage.getItem('todos')) || []
//2添加一个监视属性,并且进行深度监视
watch: {
      todos:{
        deep:true,
        handler(value){
          localStorage.setItem('todos',JSON.stringify(value))
        }
      }
    },

9、组件自定义事件

9-1、组件的自定义事件

  1. 一种组件间通信的方式,适用于:子组件 ===> 父组件
  2. 使用场景:A是父组件,B是子组件,B想给A传数据,那么就要在A中给B绑定自定义事件(事件的回调在A中)。
  3. 绑定自定义事件:
  1. 第一种方式,在父组件中:<Demo @at1="test"/>  或 <Demo v-on:at1="test"/>
  2. 第二种方式,在父组件中:
<Demo ref="demo"/>
    ......
    mounted(){
      this.$refs.xxx.$on('at1',this.test)
    }
  1. 若想让自定义事件只能触发一次,可以使用once修饰符,或$once方法。
  1. 触发自定义事件:this.$emit('at1',数据)
  2. 解绑自定义事件this.$off('at1')
  3. 组件上也可以绑定原生DOM事件,需要使用native修饰符。
  4. 注意:通过this.$refs.xxx.$on('at1',回调)绑定自定义事件时,回调要么配置在methods中要么用箭头函数,否则this指向会出问题!

9-2、TodoList案例添加自定义事件

MyHeader中的:addTodo="addTodo"改成@addTodo="addTodo"

然后把props中的addTodo删掉,然后使用

事件名.$emit(addTodo,value)

//1将这里的<MyHeader :addTodo="addTodo"/>改成
<MyHeader @addTodo="addTodo"/>
//2找到props中可能存在的addTodo,然后删掉
//3在methods里面的add中添加this.$emit('at1',数据)
this.$emit('addTodo',todoObj)
目录
相关文章
|
2月前
|
缓存 JavaScript 前端开发
vue2.0+vue3.0资料(尚硅谷)(一)
vue2.0+vue3.0资料(尚硅谷)
64 0
|
2月前
|
缓存 JavaScript 前端开发
vue2.0+vue3.0资料(尚硅谷)(五)
vue2.0+vue3.0资料(尚硅谷)
82 0
|
7月前
|
JavaScript 前端开发 API
尚硅谷Vue3 笔记总结及代码-1
尚硅谷Vue3 笔记总结及代码-1
208 0
|
2月前
|
JavaScript 搜索推荐 程序员
vue2.0+vue3.0资料(尚硅谷)(三)
vue2.0+vue3.0资料(尚硅谷)
33 0
|
2月前
|
存储 JavaScript 前端开发
vue2.0+vue3.0资料(尚硅谷)(六)
vue2.0+vue3.0资料(尚硅谷)
63 0
|
2月前
|
JavaScript 前端开发 API
vue2.0+vue3.0资料(尚硅谷)(七)
vue2.0+vue3.0资料(尚硅谷)
76 0
|
2月前
|
JavaScript 前端开发 安全
vue2.0+vue3.0资料(尚硅谷)(二)
vue2.0+vue3.0资料(尚硅谷)
82 0
|
9月前
|
缓存 JavaScript 网络架构
[Vue]学习笔记目录 【Vue2与Vue3完结】 (尚硅谷Vue2.0+Vue3.0全套教程丨vuejs从入门到精通)
[Vue]学习笔记目录 【Vue2与Vue3完结】 (尚硅谷Vue2.0+Vue3.0全套教程丨vuejs从入门到精通)
|
16天前
|
JavaScript 前端开发 API
Vue 2 vs Vue 3:开发者之争,究竟选择哪个版本?
Vue 2 vs Vue 3:开发者之争,究竟选择哪个版本?
28 1
|
9月前
|
JavaScript 前端开发 API
[Vue]Vue3学习笔记(尚硅谷)(三)
[Vue]Vue3学习笔记(尚硅谷)(三)