终于顺利进入vue了,也确实是学了之后,之前三遍vue没学过确实没错,现在一点也不后悔,ajax,Node.js、promise、webpack、git等,除了这三个基础之外,确实是需要学习的。终于可以一窥vue的真面目了。学了这么久,一直忍着不说实话。我不想碰这条线。就是想保持浓厚的兴趣,看看vue到底是个什么神奇的东西。它可以使代码如此简单。确实,至少在我现在学习的阶段,我没有其他大的感受。唯一的感觉就是很多功能的实现都轻松了很多,比nativejs简单的不是一点半点。我在中间丢失了笔记。感觉也许typora会让我学两个版本加深记忆。总是有这个错误。占用的存储空间还在,打开是一片空白。反正我已经和typora的制作组沟通过了。我已经联系了,看看以后能不能解决这个bug。这篇文章可谓是重量级的,至少是我目前为止最大的合集格式、含金量、规模!一、Vue简介1、Vue是一套用于构建用户界面的渐进式(progressive:自上而下的应用程序,一个引入各种vue插件的小型核心库)JavaScript框架。2.特点采用组件化方式,提高代码复用率,让代码更易维护:一个.vue后缀的文件,将html、css、js全部打包在一起,完成一个活动版块的内容。这就是组件化;codereuseRate:既然你封装好了,我直接用,就是代码复用率;代码更易于维护:我直接在你的基础上修改了一些功能。声明式编码在了解什么是声明式编码之前,首先要了解什么是命令式编码。我们以前都是通过原生js一步步渲染一个数据对象到页面,就像一步步完成别人的订单一样这是命令式代码,我们的声明式代码只需要声明一下即可。使用虚拟DOM+Diff算法复用DOM节点。本来,我们使用原生的js,通过模板字符串或者模板引擎来渲染数据。如果这时候新增几条数据,我们就得从头渲染,生成一个完整的html,然后去掉我们新增的,生成一些之前的字符串(之前的数据),所以vue的做法是移动虚拟dom,而diff算法会比较virtualdom是否有和之前一样的直接多路复用。二、搭建vue开发环境1、安装打开vue官网安装开发版。引入vue.js后,日志中会有两个提示:一个是让你下载开发者工具,一个是提醒你上线后不要导入这个vuejsVue代码提示插件:vue3Snippets2.DeveloperToolsGoogleAppStore下载vue-devtools注意修改vueGoogle插件3.productionTip是我们的第二个提示,参考vue官网api这是我们vue全局配置下的属性,也就是propertyvue.config的字面意思是生产环境提示,改为false。此后所有提示均已删除。三、Vue基础1.hello小案例在进入这个案例之前,先解决一个问题。首先我们要知道我们的vscode打开liveserver后,他把整个vscode文件夹都放在了server下面,于是他回到server根目录下找到这个小图标,在根目录下添加这样一个图标使用vue的目录。一开始需要创建一个vue对象实例,最主要的是,实例中要传递的参数:el:''==el是一种固定的写法,后面的值通常是cssselector==data:{}==data也是一种固定的写法,暂时写成一个对象,作用就是给上面的el传递参数,也就是容器====总结:==想让vue工作,必须配置一个vue实例,里面的参数是一个对象容器(divbox),也叫vue模板。一种是插入vue语法,另一种是运行js的时候看到vue实例,然后vue.js会回去扫描这个容器。扫完还是有vue的语法,然后会看数据有没有这个key,这样就完成了一个转换过程。其实这个原理有点类似于前面说的模板引擎!1.1.注意事项我们的容器(vue模板)和实例是一对一的关系。如果写两个类名相同的vue模板,写一个实例,两个都不会渲染。只有第一个A模板有数据;你写了一个模板,但是有两个实例,对应这个模板,分别传入两个数据,不会渲染数据,只有第一个实例有数据。实际开发中只会有一个容器和一个实例(这里数据会进行组件化开发)。我们容器中的vue语法{{}}中的内容只能是表达式表达式:是一个有值的公式,比如变量、函数、三元表达式、算术运算等js代码:if、for循环,这两个要区分:修改数据可以在开发者工具中修改2.模板语法插值语法,即上面使用的插入输入值指令语法:==v-bind:可以简写为:==注意(专门针对tag属性中的字符串,让它成为一个表达式,相当于有了Value,它是一个变量,我们需要在实例中找到这个值)所以我们一般使用插值语法来应用标签体,v-bind用于标签属性3.数据绑定数据绑定有两种类型:单向绑定设置==v-bind==只会使属性受到影响数据,但数据的修改不会影响属性。双向绑定:==v-model==value在变,data数据也在变==v-model:value可以直接简写为:v-model没有冒号,因为是用来收集的thevalue====注意==:双向绑定一般只用在表单元素上(input,radio,check,textfield等)4.el和el的两种写法数据首先要知道我们vue实例对象上有很多$开头的方法。这些方法是给我们使用的,但是不以$开头的是vue自己使用的,我们不能使用。el的第二种写法就是在prototype上直接使用实例对象的proto==$mount==方法(综合记忆,mount是挂载的意思,我们vue本身就是把这个实例挂载到这个容器中),这样既这个还好,面对不同的情况,有不同的用法。data的缩写method是一个函数,==但是函数的返回值只能是一个对象==缩写为==注意:vue管理的函数(比如data函数),不能写箭头函数,否则这就是一团糟,不再是vue对象实例。模板,将模板的值保存到数据中,中间进行一次转换工作。这就是VM,整个系统就是MVVM模型==所以我们一般把对象实例命名为vm,中间的转换过程就是我们需要学习vue的各种语法====总结==:回顾我们可以在前面提到的{{}}vue方法中编写什么。上面说的这个表达式其实这里能写的远不止这些。我们的vm是一个实例对象,而{{}}里面的东西其实就是我们vm实例对象里面的任何东西,包括我们data里面写的名字,年龄等等。所以我们可以使用它。不仅如此,连原型上不以$开头的都可以获取到,而且不需要加前缀。我认为它们都在虚拟机中。之所以这么说只是为了记住我们模板中的vue语法都是获取到的vm实例中的属性方法。6.数据代理需要用到之前学过的一个es6语法Object.defineProperty(字面意思可以看出定义属性,即定义对象的属性),这个方法有三个参数,第一个是对象名称,第二个是对象属性的名称,第三个参数是一个配置对象。里面有四个值可以约束这个属性。枚举表示是否可以遍历。上面只是这个方法的一个普通用法,真正使用的是配置对象这两个方法如果我们这样定义:可以看到值不会改变,为什么呢?因为我们都知道js代码的执行顺序加上我们的时间循环机制,所以我们在第一次定义数字的时候,随着主要栈道一起定义数据,我这时候会修改数字的值,那么只是修改number的值不会重新执行data的重新赋值,他的修改不会影响到他。所以这个时候我们的defineProperty配置对象中有两个方法==get函数(getter)。当有人访问age的值时,会立即调用getter====set函数(setter)。当有人修改age为值时,我的value形参会收到这个值,这样就可以用来修改我里面数据的值了==数据代理使用对象代理来操作(读写)vue中另一个对象的属性数据代理首先,我们定义的数据会被vue转换成它下面的_data对象。其实vue做到这一点就够了。我们在传输数据的时候,只需要_data.name,但是大家有没有想过呢?我们没有传递任何数据,所以之前添加数据很麻烦,所以Vue接着做了一个数据代理的事情,给vm实例添加了两个新的属性name和age,其实就是使用方法defineproperty添加的,同时,getter返回_data.name的值,setter修改它的值。这里有一个数据代理,vm实例对象用来代理_data对象。7.事件处理7.1事件基本用法==事件命令语法v-on:click(命令语法全部以v-开头)====vm实例对象属性为methods==是时间处理函数的属性名How我们将参数传递给事件吗?前面说了,命令语法会将字符串变成表达式,所以这里的字符串不再是字符串那么简单,它是一个函数,如果是函数,可以给它一个实参event。如果要使用内置对象事件,还需要在==$event中传入参数====注意:==v-on:xxxxxx为事件名称。这是vue的事件声明方法。==可以简写为@xxx==我们的事件处理函数也会成为vm实例上的函数。这些函数也是vue管理的函数,所以不要使用箭头函数。如果指令语法不传参数,处理函数还有一个一个形式参数,这个参数默认为e内置对象7.2事件修饰符表示不需要执行一些通过e.~~操作,可以直接在命令语法中使用,==看下面的案例,注意这个事件修饰符加在哪里==(记住前三个)(可以写成链式编程)==prevent:防止默认行为====stop:防止冒泡====once:事件只触发一次====capture:使用捕获模式==怎么理解,因为我们默认的事件是先被捕获只是冒泡,但是事件处理是在冒泡中进行的,即parent和child都有一个打印信息。我的思路是先读parent再读child,因为先捕获了事件,但是我们的事件handler是在冒泡的,所以冒泡回去的时候先打印child再打印parent.这时候如果给parent添加一个capture,就意味着流程将从事件捕获开始。首先捕获事件流本身。我的想法是事件流来了。由于事件是在捕获阶段触发的,所以会先打印parent,再打印child。正常逻辑,我点击div2,会按照冒泡21加capture后执行==self:只有e.target是当前操作元素时才会触发(可以用来防止冒泡)==显然是这样的又会开始冒泡,不过我在父元素上加了一个.self事件修饰符,也就是说只有当e.target是我自己的时候才会触发他的点击事件,我们知道谁触发了e.target。虽然点击div4触发了两次,但是两次都是div4被动的元素:==知识扩展二==:我们的滚动事件有两种,一种是==scroll==当我们滚动滚动条时触发,而另一个是==wheel==当我们滚动鼠标滚轮时触发。这时候我们会发现,当我们移动鼠标滚轮的时候,需要先执行回调函数。完成后,将执行向下滚动的默认行为。这时候被动就派上用场了。7.3键盘事件注意在哪里以及如何使用它。特殊按键tab:必须和keydown一起使用,因为按了会切换,keyup等你抬起按键,已经被切掉了,按这个按键要实现的功能是实现不了的。系统修改键如上图第三点,扩展名:@keyup.ctrl.y=xxx表示只能ctrl+y触发如果你要使用的键在定义之外,你可以先通过e.key查看key的名称。一般键盘上的名字有些不同,比如ctrl=control,得到名字后==如果有两个字及以上用驼峰命名(CapsLock)==,需要大写转小写,和用-分隔单词,比如:caps-lock,可以正确使用这个键8.计算属性名案例:输入姓氏,输入姓名,显示,动态显示。插值语法实现:methods方法实现我们的vue语法可以是一个函数,只要把函数写在methods中,这个方法的重点是首先我们的事件处理函数确实可以省略括号,但是不能在vue语法中省略,然后我们需要知道我们的数据在vm实例中,而我们vue管理的函数this也是一个vm实例,所以我们可以取==计算属性==将==已经写入的属性==go处理计算形成一个新的属性,需要写在==computed==属性中。firstname和lastname是我们vm的属性,fullname也是vm的属性(所以也直接用Vue语法),不过是计算属性。属性计算属性中每一个需要用来操作已有属性的属性都需要一个getter和setter,就像定义obj的属性的方法一样。当有人访问这个属性(fullname)时,会调用getter,它的返回值是什么时候fullnameget的值被调用?computed中的getter有缓存机制,也就是说如果一个vue模板中多个地方使用了fullname,getter只会被调用一次。调用时分为两种情况:一种是第一次读取计算属性时,另一种是计算属性的依赖数据发生变化时(依赖数据是里面this.xxx的数据),所以它跟上面的方法最本质的区别就是它有缓存机制。如果多次使用这个值,只要依赖的数据没有变化,就只会调用一次。但是,methods中的函数方法只调用一次。同时注意不要把它看得太复杂,它只是一个属性。Vue语法调用时,也是根据属性调用。里面的函数只是修改了这个属性,可以理解为模板引擎中的fileterNamesettersettersettersettersetter他还有一个二传手。如果这个属性只是计算出来给别人看的,你可以不用写这个setter。如果这个计算出来的属性会被修改,需要一个setter==简写==:前提是只读不写(没有Setter)这里还是一个属性,只是简写,不要像Vue里的函数那样调用语法很简单。一句话就可以直接命令语法==监控方法一:通过一个新的配置==watch==,写你要监控的属性也是一个对象,然后写配置项==handler==function其中有两个参数,一个是变化后的最新值,一个是变化前的值;第二个配置项==immediate==是一个boolean值,表示是让hanlder一开始就执行还是改变执行监听方式2:通过vm实例中提供的方法==$watch====注意对象中的属性名本质上是一个字符串,所以这里需要传入一个字符串==deep监控Vue的watch默认是不检测对象中的值的,需要配置==deep==只有在watch中才能你检测对象是否发生了变化==监控简写==类似于计算属性,没有其他配置项,只有handler可以简写方法2也可以简写,前提是一样的==总结:目前的功能vue管理(不能写箭头函数)===>计算属性中的methods、getters、setters(包括缩写),监控属性handlers包括缩写
