首发于 vue3

Vue基础

vue 是什么?

1.vue是渐进式javaScript框架 html5--->css3--->js web里的渐进式(可以逐渐的使用,逐渐的进步,不需要完全使用) vue中渐进式:声明式渲染---->组件系统---->客户端路由--->大规模状态管理--->构建工具 2.库和框架 库就是封装的属性和方法 框架:拥有自己的规则和语法,在他的框架里面去开发遵循他的语法

vue 安装环境以及创建项目

  1. 安装node .js Node.js 官网: nodejs.org/en/download
  2. 安装 cnpm npm install -g cnpm --registry= registry.npm.taobao.org 或者安装yarn cnpm install -g yarn
  3. 安装vue-cli 3.x脚手架(@vue/cli全局包) 免去了webpack的配置,脚手架就是搭建一个项目的环境。支持css less 开发服务器的支持,babel的支持 cnpm install -g @vue/cli 或 yarn global add @vue/cli 检查:vue -v 安装完成以后 得到了一套vue 的环境以及命令 服务等

vue脚手架文件说明

1.src: components子组件 App.vue 是跟组件,子组件都要挂载到跟组件中 main.js 是webpack的打包入口文件,会把src下的所有资源,都会被webpack打包后,才会插入到index.html上,然后交给浏览器去运行 babel,config.js:babel降级的配置规则 package.json : 当前项目需要的依赖包,还可以自己定义命令 yarn.lock:项目包版本锁定和缓存地址

vue 主要的3个文件和关系

1.当执行yarn serve时,就会进行webpack打包项目
2.打包时候就会执行入口文件,main.js,在里面实例化了一个vue对象

vue 开发服务器的自定义配置

在vue.config.js(是vue脚手架项目中默认配置文件名)中配置,
webpach+node环境,导出配置对象使用moudule.exports
module.exports = {
devServer :{
  port:3000,
  open:true
lintOnSave:false  //关闭代码检查
1.vue-eslint 代码检查,关闭

vue 的设计模式:MVVM

操作dom vue源码就干了,数据驱动了试图的改变,我们只需要操作数据
View(就是template层,dom层)-----ViewModel(
vue 的源码,1.监听Model层数据的改变,然后吧值赋值到View层,就是template层
2.当你视图层View改变,ViewModel监听你输入的值改变了,然后吧值赋值给Model层)-----Model层(数据层,就是声明的变量)

vue 单页面开发方式介绍

1. 每一个vue文件吧代码分了3部分
    template:标签 html 这里面必须有一个根标签
    script:js,vue中所有的变量定义
    style:样式,scoped可以保证样式只对当前有效

vue 指令

指令解释 :vue中有很多的指令,放在标签上,以v-开头的,称之为指令,每一个指令都能提供一个功能

## vue的插值表达式(生命时渲染/文本插值)

作用:改变标签的内容,以前使用:innerHtml 语法:{{表达式}} 1. 变量 2.对象 3. 表达式 vue中的数据变量要在js中的data函数里的return的对象上声明


     export default {       
data(){         
return{             
msg:"你好vue",             
age:7,             
obj:{                 
name:"第一次学习vue",                 
age:30            
 }     } 

v-bind 指令

指令就是提供的一个功能
目的:给标签的属性设置值,把vue变量的值,赋值给标签的原生属性上 例如 <a href="">百度一下</a>
语法:v-bind:属性名='vue变量'
简写::属性名='vue变量'
<a :href="url就是vue的变量名字">百度一下</a>

v-on 绑定事件

目标:给标签绑定事件, eg:点击事件
语法:v-on:事件名=”要执行的少了代码“
     v-on:事件名="methods中的函数名"
     v-on:事件名=”methods中的函数名(实参)“
简写: @click="methods中的函数名"
      @change="methods中的函数名"
this指向的是export default 的{}的组件上,data函数会把对象挂到当前组件的对象上
<button @click="fun1()">点我吧+1</button>
 methods:{
    fun1(){
        this.num+=1
  }

vue事件_接收事件对象

目的:获取事件对象,例如:阻止标签的默认应为时,vue事件处理函数中,拿到事件对象
    无参数,通过形参直接接受 形参声明e
    传参数,通过$event指代事件对象传给事件处理函数
    one(e){
        e.preventDefault() #阻止事件默认行为
    one(num,e){
        e.preventDefault() #阻止事件默认行为
    }

vue事件_修饰符

目的:在事件的后面.修饰符 给事件带来了更强大的功能
语法:@事件名.修饰符="methods里函数"
    @change
    @click.stop
修饰符列表:
    1.  .stop:阻止冒泡,阻止向父级冒泡
    2.  .prevent :阻止默认行为
    3.  .once:程序运行期间,只触发一次事件处理函数,事件还是在一直的执行,只是函数触发一次而已
    @click.stop=”btn“
    <div @click="father()">
    <p @click.stop.once="son()">点我父亲不冒泡,正常标签的点击事件会向父级           冒泡的</p>
    </div>

vue按键_修饰符

目的:给键盘事件,添加修饰符,增强功能
    @keydown.enter  监测回车键
    @keydown.esc    监测返回按键
    <input type="text" @keydown.enter="enterFun()">
    <input type="text" @keydown.esc="escFun()">

v-model

目的:value属性和vue数据变量,双向绑定在一起
语法:v-model='vue数据变量'
用在哪里:目前v-model暂时用在表单标签上
双向数据绑定
 - vue数据变量变化---》视图value属性自动同步
 - 视图value属性变化---》vue数据变量自动同步
input输入框:
 用户名:<input type="text" v-model="username">
下拉框:select v-model写在 select上
<select name="" id="" v-model="from">
    <option value="0">北京</option>
    <option value="1">天京</option>
    <option value="2">上海</option>
</select>
    vue的变量应该定义为数组:bobby:[], 关联的value的值
    如果定义非数组关联的是复选框的checked属性上
    <input type="checkbox" value="1" v-model="hobby">抽烟
    <input type="checkbox" value="2" v-model="hobby">喝酒
    <input type="checkbox" value="3" v-model="hobby">写代码
    <input type="radio" value="男" name="sex" v-model="gender">
    <input type="radio" value="女" name="sex" v-model="gender">
textarea:文本域
    <textarea name="" id="" cols="30" rows="10" v-model="textall">      </textarea>

## v-mode修饰符 目的:让v-model拥有更强大的功能 输入框输入的类型是字符串的,可以转换输入的值 语法: - v-model.number = 'vue的变量名' 以parseFloat转成数字类型 - v-model.trim='vue的变量名' 去除首位空白字符 - v-model.lazy='vue的变量名' 在change时触发非input时(就是失去焦点的时候才会赋值给vue变量)

## v-text和v-html

目的:更新dom对象的内容innerText/innerHtml,可以把vue的变量值,设置成标签显示的内容

语法:

- v-text='vue变量' 把vue变量的值当前普通字符串显示

- v-html='vue变量' 能解析html内容当前标签显示 给元素的内容 ,把变量的内容当html内容渲染到标签中去

## v-show 和v-if

目的:控制标签的显示或者隐藏

语法:

- v-show='vue变量true/false',只能跟true或者false,或 表达运算符结果是布尔类型,控制标签的显示与否

- v-if="vue变量" 只能跟true或者false,或 表达运算符结果是布尔类型,控制标签的显示与否

区别:

v-show:用的

v-if 直接从dom树删除了

## v-for

目的:列表渲染,所在标签结构,按照数据数量,循环生成,想要谁循环就把v-for写到谁身上
    - 目标结构:变量数组,对象,数字
    - v-for="(变量值,索引变量) in 目标结构" 
    - v-for = "变量值 in 目标结构(vue循环的变量)"
    - v-for='(value,key) in 对象' 
    - v-for="变量名 in 固定数字" 是从1开始遍历
    - :key一般写索引不重复的 这个值来是优化循环用的
    key的作用:
        - 无key:最大限度尝试就地更新复用相同类型标签内容更新了
        - 有key:基于key的值来比较新旧虚拟dom,移除key不存在的元素 与无key一样的
     <li v-for="(arr_s,i) in arr" :key="i">{{arr_s}}-       {{i}}
 arr:["小名","小红","大黄"]
    <li v-for="stu in stuArr" :key="stu.id">{{stu.name}}</li>
 stuArr:[
  {"id":"1","name":"张三","age":19},
  {"id":"2","name":"张三1","age":192},
  {"id":"3","name":"张三2","age":1933}
 ]

在script中引入图片

import imgobj  from './assets/1.gif'
唯独js需要导入图片(css和标签里面直接使用图片地址)

虚拟DOM

采用的diff算法,对新旧的虚拟dom进行同级比较,根元素变化,删除重新创建

动态clss

目标;用v-bind给标签class设置动态的值
语法: :class="{style的类名:布尔值true使用,false不用}"

动态style

目标:给标签动态设置样式
语法: :style="{css属性名:值或者vue的变量}"
<p v-if="age>18" :style="{color:'yellow'}">成年</p>

案例

arr:[]
列表追加:arr.push(1)
数组的删除:arr.pop()
shift()头部删除  unshift()头部追加  sort()排序
删除:arr.splice(数组下标,1)
获取列表的索引:indexof或者arr.findIndex(obj=>obj.id=id) obj是数组的每一个对象
获取数组最后一个索引:arr.length-1
列表数据反转:arr.reserver()
字符串分割:str.split(',') 生成一个数组
数组转换成字符串:arr.join("")

过滤器

目的:转换格式,过滤器就是一个函数,把一个东西传递进去,返回一个处理的值
使用:过滤器只能用在,插值表达式和v-bind动态属性里
     {{vue 变量值 | 过滤器名 }} 把值传递给了过滤器中
     :title="vue变量值 | 过滤器名 "
    1.全局过滤器在App.vue 中定义 Vue.filter("过滤器名",(值1,值2)=>return ”返回你处理后的值”) 插值表达式中使用{{msg | 过滤器名 }}
    2.在某一个.vue中定义局部定义,定义在和data同级,filters:{过滤器名字:(值)=>{return ”返回你处理后的值”}}
vue中过滤器的场景(举例):
    1.字母的大小写转换
    2.字符串反转

给过滤器传参

语法:
    1. vue 变量 | 过滤器名(值)
    Vue.filter("过滤器名",(值1,值2)=>return ”返回你处理后的值”)
    值1:vue变量,值2:过滤器传递的值
    2.多个过滤器:vue 变量 | 过滤器名1 | 过滤器名2
  案例:时间格式化:YYYY-MM--DD格式
    1. 安装:moment模块 yarn add moment
    2. 导入:import moment(取一个名字) from ‘moment’
    3. 使用:moment(传递一个时间值).format('YYYY-MM-DD')

计算属性_基础

目标:一个变量的值,依赖另外一些数据计算而来的结果,
语法:computed:{
        "计算属性名"(值){
            return "值"
注意:计算属性名和data里的属性都是变量,不能重名 
特点:函数内变量改变,会计算新的值,计算属性也是一个变量

计算属性_缓存特性

目标:计算属性,基于依赖项的值进行缓存,依赖的变量不变,都直接从缓存取结果
 计算属性优化:带缓存,计算属性对应的函数执行后,会把teturn的值缓存起来,依赖项不变的多次调用都是从缓存取值,依赖改变了,函数会重新执行,并缓存新的值
 依赖项:就是你的使用的变量
 案列:求数组的价格的和,平均值
    数组求和:this.list.reduce((sum,obj)=>sum++obj.price,0)
    求均价:toFixed(2)保留2位小数

计算属性_完整写法

计算属性也是一个变量,给计算属性赋值,需要set
目的:当有人要给计算属性赋值的时候,才需要set使用完成写法
computed:{
        "计算属性名例如full":{
            //给full赋值触发set方法,就是改变full变量的值
            set(值){},
            // 使用变量的值触发get方法
            get(值){retrun "值"}
}

监听器_watch

目的:可以监听data里面的变量/computed属性值的改变
语法: watch:{
    "被监听的属性名"(newval,oldval){
    用户名:<input type="text" value="123" v-model.trim="username">
    watch:{
        username(newValue,oldValue){
            console.log(newValue,oldValue)
    },

监听器_深度监听和立即执行

目的;监听复杂类型(对象/数据),或者立即执行监听函数
     watch:{
        "被监听的属性名":{
            immediate:true //立即执行(网页打开handler就执行了一次)
            deep:true //深度监听负载类型的变化
            handler(newvalue,oldval){
    }

数据缓存_localStorage

存入的是字符串
    localStorage.setItem('key',value)
    JSON.stringify(列表) 把列表转成json字符串
    JSON.parse(json字符串) 把json字符串转成json
    localStorage.getItem('key')

vue组件:每一个组件都是独立的

- vue组件的创建和使用
    1. 引入:import  pub(组件对象,变量名字随意取的)  from './components/public.vue';
    2. 注册:
        全局注册:在main.js中Vue.components("组件名字",组件对象)
        局部注册:某一个vueapp中components:{pub,}或者{组件名字:组件对象}
    3. 使用:在template下,组件名当做标签使用  <pub/> 或者<pub></pub>
- scoped作用过程:
    webpack打包的时候把当前组件内标签都被添加了data-v-hash值的属性,所有的css的选择器都加一个hash的属性选择器

vue的组件通信

- 父传子_props
  目标:父组件--->子组件传值,首先明确父和子是谁,在父引入子(被引入的是子)
  例如:父:App.vue子:Myproduce.vue
      1.子组件内,定义变量,准备接收,然后使用变量
        props:['title','price','info'] 里面都是变量 使用定义的变量
      2.父组件 给对象的子组件定义的变量传递值进去
        <product title='好吃的' price='50' :info='str'></product>
- 父向子传递_使用v-for循环组件
- 组件通信_单向数据流
    目的:从父到子的数据流向,叫单向数据流
    1.子组件修改父组件传入的数据,不通知父组件,会造成数据的不一致性,而子组件依赖父组件传入的值vue规定
    2.props里面的定义的变量本身只读的不允许重新赋值
- 组件通信_子向父(当儿子要改变父组件的数据)
    目的:子组件触发父自定义事件方法
    1.父组件内,绑定自定义事件和事件处理函数
    2.子组件内,触发父给我绑定的自定义事件,导致父methods里事件处理函数的执行,使用this.$emit(’父亲事件名字‘,’传值‘)触发事件
    语法:@自定义事件名字=‘父methods里面的函数名’
- 2个没有任何引入关系的组件,怎么通信?
  跨组件的传值:App.vue 中引入2个子组件,2个子组件传值,创建一个空白的Vue对象,监听和触发,移除事件只有这3个功能,接收方 绑定一个事件,使用: 事件.$on('事件名',函数体) 主动方   事件.$emit('事件名',值)
        1. src/EventBus/index.js 下创建一个空白的Vue对象并导出
            EventBus(文件夹)/index.js  名字随意写
            import Vue from 'vue'
            export default new Vue()
        2.在要接收方的组件(List.vue)  
           a. 先引入EventBus这个文件夹下的index.js  
              import enventBus from '../EventBus' 如果文件夹下的名字叫                  index.js 会自动找不用写全了,否则路径要写全了
           b. created(){
                 eventBus.$on('send',(index,price)=>{
                    "代码块" send 自动义的事件名字
                    $on注册事件
        3.在要传方的组件(Myproduct.vue)eventBus.$emit('事件名',值)
           a. 先引入EventBus这个文件夹下的index.js