基础知识

基础环境

  • vscode
  • 所需的插件:

jshint:JS代码检查
Beautify:代码美化(选中代码-->format doc)
Vetur: Vue插件
JavaScript (ES6) code snippets: ES6语法
Auto Rename Tag: 自动重命名标签
Vue-helper:Vue提示
vscode-icons: 文件夹图标
open in browser

vscode快捷键

ctrl+k以及ctrl+s打开快捷键窗口,以便查看快捷键

Vue 介绍

是一套构建前后端分离的架构

Vue的安装和使用

三种方式:

  • script标签引用
<!-- development version, includes helpful console warnings -->
<script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
<!-- production version, optimized for size and speed -->
<script src="https://cdn.jsdelivr.net/npm/vue"></script>
  • npm安装
  • vue-cli安装

Vue体验

<!DOCTYPE html>
<html lang="en">

<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <meta http-equiv="X-UA-Compatible" content="ie=edge">
  <script src="../lib/vue.js"></script>
  <title>01VueStudy</title>
</head>

<body>
  <div id="app">
    <p>{{ greet() }}</p>
    <p>{{ username }}</p>
    <button @click="username='隔壁老王'">更改值</button>
  </div>
</body>
<script>
  new Vue({
    el: '#app',
    data: {
      username: "Hello"
    },
    methods: {
      greet() {
        return "你好啊"
      }
    }
  })
</script>

</html>

Vue的模板语法

  • v-bind: 属性绑定
  • v-once: 在模板中只读取一次变量,后续变量更改了,不会跟着变化
  • v-html: 解析html标签
<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <meta http-equiv="X-UA-Compatible" content="ie=edge">
  <script src="../lib/vue.js"></script>
  <title>vue v-bind</title>
</head>
<body>
  <div id="app">
    <p v-once>{{ username }}</p>
    <p v-html='code'>{{ code }}</p>
    <button @click="username='隔壁老王'">改变</button>
    <img v-bind:src="logo" alt="">
  </div>
  
</body>
  <script>
    new Vue({
      el: "#app",
      data: {
        username: "Alex",
        code: "<a href='https://www.baidu.com'>BAT</a>",
        logo: "https://vuejs.org/images/logo.png"
      }
    })
  </script>
</html>

Vscode添加自定义代码片段

  1. ctrl+shift+p
  2. 搜索Snippets关键字,选择Preferance
  3. 选择html.json,修改成如下的样子
{
 "my vue html code": {
  "prefix": "html",
  "body": [
   "<!DOCTYPE html>",
   "<html lang='en'>",
   "<head>",
   "    <meta charset='UTF-8'>",
   "    <meta name='viewport' content='width=device-width, initial-scale=1.0'>",
   "    <meta http-equiv='X-UA-Compatible' content='ie=edge'>",
   "    <script src='../lib/vue.js'></script>",
   "    <title>$1</title>",
   "</head>",
   "<body>",
   "    <div id='app'>",

   "    </div>",
   "</body>",
   "    <script>",
   "    new Vue({",
   "    el: '#app',",
   "    data: {",
   " $2",
   " }",
   "    })",
   "    </script>",
   "</html>",
  ],
  "description": "my vue html code"
 }
}

属性绑定

  • 绑定class的两种形式
<!DOCTYPE html>
<html lang='en'>
<head>
  <meta charset='UTF-8'>
  <meta name='viewport' content='width=device-width, initial-scale=1.0'>
  <meta http-equiv='X-UA-Compatible' content='ie=edge'>
  <script src='../lib/vue.js'></script>
  <title></title>
  <style>
    .title{
      font-size: 20px;
      color: red
    }
    .main-title{
      font-weight: 1800;
    }

  </style>
</head>
<body>
  <div id='app'>
    <!-- 数组方式 -->
    <p v-bind:class="[pclass1,pclass2]">I like Vue</p>
    <!-- 对象方式 -->
    <p :class="{'title':true,'main-title':strong}">我是隔壁老王</p>
    <button @click="strong=true">文字加粗</button>
    <!-- 对象方式 -->
    <p :style="{backgroundColor:backgroundColor}">属性绑定样例</p>
    <!-- 数组方式 -->
    <p :style="[Pstyle1,Pstyle2]">属性绑定样例2</p>
  </div>
</body>
  <script>
    new Vue({
      el: '#app',
      data: {
       pclass1: "title",
       pclass2: "main-title",
       strong: false,
       backgroundColor: "red",
       Pstyle1: {
         'background-color':'blue',
         'font-size': '30px'
       },
       Pstyle2: {
         "border-bottom":"2px solid #000"
       }
     }
    })
  </script>
</html>

使用JS表达式

在属性绑定和变量读取中,可以使用表达式。常见的表达式有: 变量读取,变量运算,三目运算符,函数调用,取反等

<!DOCTYPE html>
<html lang='en'>
<head>
  <meta charset='UTF-8'>
  <meta name='viewport' content='width=device-width, initial-scale=1.0'>
  <meta http-equiv='X-UA-Compatible' content='ie=edge'>
  <script src='../lib/vue.js'></script>
  <title></title>
</head>
<body>
  <div id='app'>
    <div :style="{color: danger?'red':'black'}">{{ message.split(" ").reverse().join(" ") }}</div>
    <div>{{ greet() }}</div>
    <div>{{ !is_adult }}</div>
  </div>
</body>
  <script>
    new Vue({
      el: '#app',
      data: {
        // 条件?条件成立的值:条件不成立的值
      // danger: true
      danger: false,
      message: "Hello World Hello China",
      is_adult: true
      },
      methods: {
        greet() {
          return "Good Morning!!"
        }
      }

    })
  </script>
</html>

条件判断

if系列

<!DOCTYPE html>
<html lang='en'>
<head>
  <meta charset='UTF-8'>
  <meta name='viewport' content='width=device-width, initial-scale=1.0'>
  <meta http-equiv='X-UA-Compatible' content='ie=edge'>
  <script src='../lib/vue.js'></script>
  <title>Vue 判断</title>
</head>
<body>
  <div id='app'>
    <p v-if="weather=='sun'">GoPark</p>
    <p v-else-if="weather='rain'">WatchMovie</p>
    <p v-else>StayHome</p>
  </div>
</body>
  <script>
    new Vue({
      el: '#app',
      data: {
       weather: "rain"
     }
    })
  </script>
</html>

多重条件使用template

<!DOCTYPE html>
<html lang='en'>
<head>
  <meta charset='UTF-8'>
  <meta name='viewport' content='width=device-width, initial-scale=1.0'>
  <meta http-equiv='X-UA-Compatible' content='ie=edge'>
  <script src='../lib/vue.js'></script>
  <title>IF</title>
</head>
<body>
  <div id='app'>
    <template v-if="age < 18">
      <p>AAA</p>
    </template>
    <template v-else-if="age >=18 && age <= 20">
      <p>BBB</p>
    </template>

    <template v-else>
      <p>CCC</p>
    </template>   
  </div>
</body>
  <script>
    new Vue({
      el: '#app',
      data: {
       age: 24
     }
    })
  </script>
</html>

method小例子

<!DOCTYPE html>
<html lang='en'>
<head>
  <meta charset='UTF-8'>
  <script src='../lib/vue.js'></script>
  <title>V-if</title>
</head>
<body>
  <div id='app'>
    <template v-if="loginType=='username'">
      <label>用户名</label>
      <input type="text" name="username" placeholder="用户名">
    </template>

    <template v-else-if="loginType=='email'">
      <label>邮箱</label>
      <input type="text" name="email" placeholder="email">
    </template>
    <button @click="changeLoginType">更换登录类型</button>
    
  </div>
</body>
  <script>
    new Vue({
      el: '#app',
      data: {
        loginType: "username"      
     },
     methods: {
       changeLoginType() {
         //三目运算符
         this.loginType = this.loginType =='username'?"email":"username"
       }
     }
    })
  </script>
</html>

小结:

  1. v-if,v-else-if,v-else
  2. 如果想要某个调间下渲染多个元素,那么就要使用template标签
  3. Vue默认会重用相同的标签来提高性能,如果不要重用的话,那就在对应的元素上加一个key属性即可

v-show和v-if的区别

v-show: 是通过简单的切换display来渲染信息,会一次性加载所有的元素,在频繁切换的状态下推荐使用,不能在template标签上使用
v-if: 真正的条件渲染,如果条件更改了,会重新加载

<!DOCTYPE html>
<html lang='en'>
<head>
  <meta charset='UTF-8'>
  <meta name='viewport' content='width=device-width, initial-scale=1.0'>
  <meta http-equiv='X-UA-Compatible' content='ie=edge'>
  <script src='../lib/vue.js'></script>
  <title></title>
</head>
<body>
  <div id='app'>
    <div v-show="loginType=='username'">
      <label>用户名</label>
      <input type="text" name="username" placeholder="username" key="username">
    </div>

    <div v-show="loginType=='email'">
      <label>邮箱</label>
      <input type="text" name="email" placeholder="email" key="email">
    </div>

    <button @click='changeLoginType'>切换登录方式</button>

  </div>
</body>
  <script>
    new Vue({
      el: '#app',
      data: {
        loginType: "username"
     },
     methods: {
       changeLoginType() {
         this.loginType = this.loginType=='username'?'email':'username'
       }
     }
    })
  </script>
</html>

循环语法

  • 循环数组
<!DOCTYPE html>
<html lang='en'>
<head>
  <meta charset='UTF-8'>
  <meta name='viewport' content='width=device-width, initial-scale=1.0'>
  <meta http-equiv='X-UA-Compatible' content='ie=edge'>
  <script src='../lib/vue.js'></script>
  <title>loop</title>
</head>
<body>
  <div id='app'>
     <table>
       <thead>
         <tr>
           <th>Index</th>
            <th>bookName</th>
            <th>Author</th>
         </tr>
       </thead>
       <tbody>
         <tr v-for="book,index in books">
           <td>{{index+1}}</td>
           <td>{{ book.title }}</td>
           <td>{{book.author}}</td>
         </tr>
       </tbody>
     </table>
  </div>
</body>
  <script>
    new Vue({
      el: '#app',
      data: {
        books: [
          {
          'title':'Book1',
          'author':'1'
          },
          {
            'title': 'book2',
            'author': '2'
          },
          {
            'title':'book3',
            'author':'3'
          },
          {
            'title': 'book4',
            'author': '4'
          }
        ]
       
     }
    })
  </script>
</html>
  • 循环对象
<!DOCTYPE html>
<html lang='en'>
<head>
  <meta charset='UTF-8'>
  <meta name='viewport' content='width=device-width, initial-scale=1.0'>
  <meta http-equiv='X-UA-Compatible' content='ie=edge'>
  <script src='../lib/vue.js'></script>
  <title>vue for</title>
</head>
<body>
  <div id='app'>
    <div v-for="(value,key) in person">
      {{ key }} : {{ value }}
    </div>
  </div>
</body>
  <script>
    new Vue({
      el: '#app',
      data: {
        person: {
          username: "alex",
          age: 18,
          homepage: "http://www.baidu.com"
        }       
     }
    })
  </script>
</html>
  • 状态保持
<!DOCTYPE html>
<html lang='en'>
<head>
  <meta charset='UTF-8'>
  <meta name='viewport' content='width=device-width, initial-scale=1.0'>
  <meta http-equiv='X-UA-Compatible' content='ie=edge'>
  <script src='../lib/vue.js'></script>
  <title>vue-for</title>
</head>
<body>
  <div id='app'>
    <div v-for="book in books" :key="book.title">
      <label>标题:</label>
      <input type="text" :placeholder="book.title">
    </div>
    <button @click="changeBookSort">更改图书顺序</button>
  </div>
</body>
  <script>
    new Vue({
      el: '#app',
      data: {
        books: [
          {
          'title':'Book1',
          'author':'1'
          },
          {
            'title': 'book2',
            'author': '2'
          },
          {
            'title':'book3',
            'author':'3'
          },
          {
            'title': 'book4',
            'author': '4'
          }
        ]       
     },
     methods: {
       changeBookSort() {
         this.books.sort(function (a,b) {
           return Math.random(0,1) - 0.5
         })
       }
     }
    })
  </script>
</html>

小结:

  • 默认情况下,如果数组中的顺序发生变化,或者个数比发生变化导致重新渲染,那么vue就会重新利用之前的元素,而不会重新排序,这样需要添加key属性,key只能支持number和string类型
  • 在vue2.2+ ,key是必须的

视图更新

针对数组中使用函数进行更新,有一下的方法直接触发更新
push/pop/sort/splice/concat/reverse/shift/unshift

<!DOCTYPE html>
<html lang='en'>
<head>
  <meta charset='UTF-8'>
  <meta name='viewport' content='width=device-width, initial-scale=1.0'>
  <meta http-equiv='X-UA-Compatible' content='ie=edge'>
  <script src='../lib/vue.js'></script>
  <title>View Update</title>
</head>
<body>
  <div id='app'>
    <ul>
      <li v-for="role in roles" :key="role">
        {{role}}
      </li>
    </ul>
    <button @click="update">更新</button>
    <button @click="update2">更新2</button>
    <button @click="popRole">删除最后一个元素</button>
    <button @click='shiftRole'>删除第一个元素</button>
    <button @click='unshiftRole'>在第一个位置添加元素</button>
    <button @click='spliceTwo'>删除前两个元素</button>
    <button @click="spliceChange">替换前三个元素中的aaa为XXXX</button>
    <button @click="spliceAdd">在第一个之前添加元素</button>
    <button @click=concatRole>合并数组</button>
  </div>
</body>
  <script>
    new Vue({
      el: '#app',
      data: {
        roles: ['aaa','bbb','ccc']       
     },
     methods: {
       // 直接赋值更新
       //通过函数更新
       update() {
         this.roles = ['ddd']
       },
       update2() {
         this.roles.push("eee")
       },
       popRole() {
         this.roles.pop()
       },
       shiftRole() {
         this.roles.shift()
       },
       unshiftRole() {
         this.roles.unshift("AAA")
       },
       spliceTwo() {
         this.roles.splice(0,2)
       },
       spliceChange() {
         this.roles.splice(0,4,'aaa','XXXX')
       },
       spliceAdd() {
         this.roles.splice(0,0,"dsadsadsa")
       },
       concatRole() {
        this.roles = this.roles.concat(['ssss','assfa'])
       }
     }
    })
  </script>
</html>

视图更新
如果想要通过下标来更新数组中的某个值,这样是不会触发视图更新的,需要通过Vue.set来实现

<!DOCTYPE html>
<html lang='en'>
<head>
  <meta charset='UTF-8'>
  <meta name='viewport' content='width=device-width, initial-scale=1.0'>
  <meta http-equiv='X-UA-Compatible' content='ie=edge'>
  <script src='../lib/vue.js'></script>
  <title>updateArray</title>
</head>
<body>
  <div id='app'>
    <ul>
        <li v-for="role in roles" :key="role">
            {{role}}
         </li>
    </ul>
    <div v-for="(value,key) in users">
      {{key}}:{{value}}
    </div>
    <button @click='updateArray'>更新Array</button>
    <button @click='updateObj'>更新对象</button>
  </div>
</body>
  <script>
    new Vue({
      el: '#app',
      data: {
       roles:["aa","bb","cc"],
       users: {"username":"BBB"}
     },
     methods: {
       updateArray() {
        // this.roles[0] = "dsadsadsd" 不能更新
        Vue.set(this.roles,0,'dadsffdafa')
       },
       updateObj() {
         this.users.username = "asdsfasfof",
         Vue.set(this.users,'age',19)
       }
     }
    })
  </script>
</html>

wanghui
34 声望9 粉丝