第一节:Vuejs入门之各种指令
一. 简介
Vue (读音 /vjuː/,类似于 view) 是一套用于构建用户界面的渐进式框架。与其它大型框架不同的是,Vue 被设计为可以自底向上逐层应用。Vue 的核心库只关注视图层,不仅易于上手,还便于与第三方库或既有项目整合。另一方面,当与现代化的工具链以及各种支持类库结合使用时,Vue 也完全能够为复杂的单页应用提供驱动。
vue是一个典型的MVVM框架
(1).M (model): 数据层 Vue 中 数据层 都放在 data 里面.
(2).V(view ): Vue 中 view 即 我们的HTML页面.
(3).VM(view-model): 控制器 将数据和视图层建立联系: vm 即 Vue 的实例 就是 vm.
二. 常用指令
1. 差值表达式:{{}}
(1). 会出现闪烁现象,原因:代码加载的时候从上往下先加载HTML 把插值语法当做HTML内容加载到页面上 当加载完js后才把插值语法替换掉所以我们会看到闪烁问题。
(2). 如何解决?
借助v-cloak指令,先声明[v-cloak]样式未display:none,然后给对应的标签上加上该指令.
2. v-text、v-html、v-pre、v-once : 都是用于内容的显示和输出,都不会出现闪烁现象
(1).v-text:输出的是纯文本,浏览器不会对其再进行html解析.
(2).v-html:会将其当html标签解析后输出,要注意预防xss攻击.
(3).v-pre:用于显示原始信息,如直接把{{msg}}显示出来.
(4).v-once:如果显示的信息后续不需要再修改,可以使用v-once,这样可以提高性能,修改值也不会跟着变化了.
3. 双向数据绑定:v-model
(1).含义:数据和视图之间同步变化
(2).使用场景:v-model是一个指令,限制在 <input>、<select>、<textarea>、components(组件) 中使用
PS: 扩展双向数据绑定的原理??
<div>{{msg}}</div>
<input type="text" v-bind:value="msg" v-on:input='msg=$event.target.value'>
4.事件的绑定:v-on
(1).用法
用来绑定事件,形式如:v-on:click="" 可以简写为@click="",可以直接再里面写业务逻辑,也可以调用方法,如果不需要向方法中传参,可以省略方法中的括号,只写方法名,如:@click="handle" 等价于 @click="handle()"
(2).传递普通参数和事件对象
对于这种@click="handle"调用方式,默认已经把事件对象传入进去了,只需要再方法中接收即可;对于@click="handle()方式调用,在最后一个参数的位置传入事件对象,事件对象为固定值:$event
(3).事件修饰符
a.阻止冒泡:传统方式在handle2中添加event.stopPropagation(); 这里可以这样:@click.stop="handle2".
b.阻止默认行为:传统方式在handle2中添加event.preventDefault(); 这里可以这样:@click.prevent="handle2".
(4).按键修饰符
格式:@keyup.常用别名,eg:@keyup.enter="handle",敲回车键的时候触发handle事件
ps: 常用的别名有:
.enter => enter键
.tab => tab键
.delete (捕获"删除"和"退格"按键) => 删除键
.esc => 取消键
.space => 空格键
.up => 上
.down => 下
.left => 左
.right => 右
(5).自定义修饰符
首先要通过event.keycode获取每个按键对应的值,然后通过代码 Vue.config.keyCodes.别名 = 按键值 进行声明,最后同上正常使用即可。比如:y对应的值是89.
注:此处官方有个bug,声明别名如果既有大写又有小写,不好用,eg:myY,不好用。
5.属性的绑定:
(1).用法: 使用v-bind进行绑定,形如 v-bind:href="xxx",可以简写为::href=""
6.样式绑定
无论绑定class,还是绑定style,都是属性的绑定,可以使用v-bind进行绑定,或者直接简写 :class:,:style。
A. class
(1).对象用法:每个样式的类名后面都要声明为true才有效,false则无效。
(2).数组用法:声明数组进行使用,或者直接简化
(3).混合使用和默认样式:默认样式单独声明一个class放进进去即可,混合使用如下
PS:如果想直接用css中的样式名称,要双重引号, :class="'xxx'",就不用再声明xxx=true之类的操作了. 多个样式的时候不推荐.
B. style
(1).对象形式
(2).数组形式:后面相同的属性会覆盖前面的,比如都有color,后面的color会覆盖前面的;不同属性则叠加
7. 分支结构和显示隐藏: v-if、v-show
(1).v-if:通过条件判断展示或者隐藏某个元素或者多个元素
(2).v-show:控制元素样式是否显示
二者的区别: v-if是动态的向DOM树内添加或者删除DOM元素;v-show本质就是标签display设置为none,控制隐藏。
8. 循环机构:v-for
(1).遍历数组:如v-for="(item,index) in myStudents,可以获取数据和索引
(2).遍历对象:从上往下排着遍历对象中的内容,如:v-for='(value,key,index) in myObj' 分别是:内容、key、索引
代码分享:
1 <!DOCTYPE html> 2 <html> 3 <head> 4 <meta charset="utf-8" /> 5 <title>基本指令</title> 6 <style type="text/css"> 7 p { 8 font-weight: bold; 9 color: blue; 10 } 11 12 [v-cloak] { 13 display: none; 14 } 15 16 .s1 { 17 border: 1px solid black; 18 height: 60px; 19 color: blue; 20 } 21 22 .s2 { 23 background-color: antiquewhite; 24 } 25 26 .s3 { 27 font-size: 22px; 28 } 29 </style> 30 </head> 31 <body> 32 <div id="app"> 33 <p>1.差值表达式</p> 34 <div>{{msg1}}</div> 35 <div v-cloak>{{msg1}}</div> 36 37 <p>2.内容的输出</p> 38 <div v-text="msg1"></div> 39 <div v-html="msg2"></div> 40 <div v-pre>{{msg1}}</div> 41 <div v-once>{{msg1}}</div> 42 43 <p>3.双向数据绑定</p> 44 <!-- 测试修改msg1后,v-once不会跟着变 --> 45 <input type="text" v-model="msg1"> 46 47 <p>4.事件绑定</p> 48 <div>{{num}}</div> 49 <button @click="num++">自增</button> 50 <button @click="handle1">自增</button> 51 <button @click="handle1()">自增</button> 52 <button @click="handle2">获取事件对象1</button> 53 <button @click="handle3(1,2,$event)">获取事件对象2</button> 54 <div @click="handle1"> 55 <button @click.stop="handle2">我要阻止冒泡</button> 56 </div> 57 <a href="https://www.baidu.com" @click.prevent="handle2">我要阻止默认行为</a> 58 <p>按键修饰符,回车触发</p> 59 <input type="text" @keyup.enter="enterHandle"> 60 <p>自定义按键修饰符</p> 61 <input type="text" placeholder="获取按键对应的值" @keyup="getKeyValue"> 62 <input type="text" placeholder="点击y键获取对应值" @keyup.yname="enterHandle"> 63 64 <p>5.属性的绑定</p> 65 <a :href="myUrl">属性的绑定-跳转</a> 66 67 <p>6.class样式的绑定</p> 68 <div :class="{s1:true,s2:true}">样式绑定-对象形式</div> 69 <div :class="[s1Class,s2Class]">样式绑定-数组形式</div> 70 <div :class="'s1'">样式绑定-直接写样式名称</div> 71 <div :class="myClass1">样式绑定-数组形式(简化)</div> 72 <div :class="myObjClass">样式绑定-对象形式(简化)</div> 73 <div :class="[s1Class,s2Class,{s3:true}]">混合使用</div> 74 75 <p>7.style样式的绑定</p> 76 <div v-bind:style='{border: borderStyle, width: widthStyle, height: heightStyle}'>对象形式</div> 77 <div v-bind:style='objStyles'>数组形式</div> 78 <!-- 样式会覆盖,后面的会覆盖前面的,没有的则添加 --> 79 <div v-bind:style='[objStyles, overrideStyles]'>数组-同属性,后面会覆盖前面</div> 80 81 <p>7. 分支结构和显示隐藏: v-if、v-show</p> 82 <div> 83 <ul> 84 <li v-if="num>=0&&num<5">一般</li> 85 <li v-else-if="num>=5&&num<10">良好</li> 86 <li v-else>优秀</li> 87 </ul> 88 <div v-show="status">v-show的应用</div> 89 <button @click="changeStatus">显示/隐藏</button> 90 </div> 91 <p>8.遍历数组:v-for</p> 92 <div> 93 <ul> 94 <li :key="index" v-for="(item,index) in myStudents">{{index+":"+item.userName+","+item.userAge}}</li> 95 </ul> 96 </div> 97 <p>8.遍历对象:v-for</p> 98 <!-- 从上往下排着显示每个值 --> 99 <div v-for='(value,key,index) in myObj'>{{key+ '---' + value + '---' + index}}</div> 100 101 </div> 102 <script src="js/vue.js" type="text/javascript" charset="utf-8"></script> 103 <script type="text/javascript"> 104 Vue.config.keyCodes.yname = 89; //给y键声明一个别名 105 var vm = new Vue({ 106 el: '#app', 107 data: { 108 msg1: "hello", 109 msg2: "<h1>hello</h1>", 110 num: 0, 111 status: true, 112 myUrl: "https://www.baidu.com", 113 //样式 114 s1Class: 's1', 115 s2Class: 's2', 116 //数组简化 117 myClass1: ['s1', 's2'], 118 //style相关声明 119 borderStyle: '1px solid blue', 120 widthStyle: '100px', 121 heightStyle: '200px', 122 objStyles: { 123 border: '1px solid green', 124 width: '200px', 125 height: '100px' 126 }, 127 overrideStyles: { 128 border: '5px solid orange', 129 backgroundColor: 'blue' 130 }, 131 //对象简化 132 myObjClass: { 133 s1: true, 134 s2: true 135 }, 136 myStudents: [{ 137 userName: "ypf1", 138 userAge: 12 139 }, 140 { 141 userName: "ypf2", 142 userAge: 13 143 } 144 ], 145 myObj: { 146 userName: "ypf1", 147 userAge: 100 148 } 149 }, 150 methods: { 151 //1. 自增 152 handle1: function() { 153 this.num++; 154 }, 155 handle2: function(event) { 156 this.num++; 157 console.log(event.target.innerHTML); 158 //阻止冒泡 159 // event.stopPropagation(); 160 //阻止默认行为 161 // event.preventDefault(); 162 }, 163 handle3: function(m, n, event) { 164 this.num++; 165 console.log(m, n); 166 console.log(event.target.innerHTML); 167 }, 168 //回车触发事件 169 enterHandle: function(event) { 170 alert(event.target.value); 171 }, 172 //获取按键对应的值 173 getKeyValue: function(event) { 174 alert("按键对应的值为:" + event.keyCode); 175 }, 176 //显示和隐藏 177 changeStatus: function() { 178 this.status = !this.status; 179 } 180 } 181 }); 182 </script> 183 </body> 184 </html>
三. 案例
1. 计算器案例
2. 选项卡案例
代码分享:
1 <!DOCTYPE html> 2 <html> 3 <head> 4 <meta charset="utf-8"> 5 <title>案例</title> 6 <style type="text/css"> 7 .tab ul { 8 overflow: hidden; 9 padding: 0; 10 margin: 0; 11 } 12 13 .tab ul li { 14 box-sizing: border-box; 15 padding: 0; 16 float: left; 17 width: 100px; 18 height: 45px; 19 line-height: 45px; 20 list-style: none; 21 text-align: center; 22 border-top: 1px solid blue; 23 border-right: 1px solid blue; 24 cursor 25 } 26 27 .tab ul li:first-child { 28 border-left: 1px solid blue; 29 } 30 31 .tab ul li.active { 32 background-color: orange; 33 } 34 35 .tab div { 36 width: 500px; 37 height: 300px; 38 display: none; 39 text-align: center; 40 font-size: 30px; 41 line-height: 300px; 42 border: 1px solid blue; 43 border-top: 0px; 44 } 45 46 .tab div.current { 47 display: block; 48 } 49 </style> 50 </head> 51 <body> 52 <div id="myApp"> 53 <p>1.计算器案例</p> 54 <div> 55 <input type="text" v-model="num1">+<input type="text" v-model="num2"> 56 <button @click="Add">求和</button> 57 <br> 58 <div>结果为:{{result}}</div> 59 </div> 60 <p>2.选项卡切换案例</p> 61 <div class="tab"> 62 <ul> 63 <!-- <li class="active">apple</li> 64 <li class="">orange</li> 65 <li class="">lemon</li> --> 66 <li :key="index" @click="Change(index)" v-for="(item,index) in list" :class="index==currentIndex?activeClass:''"> 67 {{item.title}} 68 </li> 69 </ul> 70 <!-- <div class="current"><img src="img/apple.png"></div> 71 <div class=""><img src="img/orange.png"></div> 72 <div class=""><img src="img/lemon.png"></div> --> 73 74 <div :key="index" v-for="(item,index) in list" :class="index==currentIndex?'current':''"> 75 <img :src="item.path"> 76 </div> 77 </div> 78 79 </div> 80 81 <script src="js/vue.min.js" type="text/javascript" charset="utf-8"></script> 82 <script type="text/javascript"> 83 var vm = new Vue({ 84 el: "#myApp", 85 data: { 86 num1: '', 87 num2: '', 88 result: '', 89 currentIndex: 0, // 选项卡当前的索引 90 activeClass: 'active', 91 list: [{ 92 id: 1, 93 title: 'apple', 94 path: 'img/apple.png' 95 }, { 96 id: 2, 97 title: 'orange', 98 path: 'img/orange.png' 99 }, { 100 id: 3, 101 title: 'lemon', 102 path: 'img/lemon.png' 103 }] 104 }, 105 methods: { 106 //相加方法 107 Add: function() { 108 this.result = parseInt(this.num1) + parseInt(this.num2); 109 }, 110 //切换 111 Change: function(index) { 112 this.currentIndex = index; 113 } 114 } 115 }); 116 </script> 117 118 </body> 119 </html>
!
- 作 者 : Yaopengfei(姚鹏飞)
- 博客地址 : http://www.cnblogs.com/yaopengfei/
- 声 明1 : 如有错误,欢迎讨论,请勿谩骂^_^。
- 声 明2 : 原创博客请在转载时保留原文链接或在文章开头加上本人博客地址,否则保留追究法律责任的权利。