2.1 简介

官网文档:https://cn.vuejs.org/v2/guide/

Vue 是渐进式 javascript 框架: 让我们通过操作很少的 DOM,甚至不需要操作页面中任何 DOM 元素,就很容易的完成 数据和视图绑定双向绑定 MVVM。使用 Vue 过程中页面中不需要再引入 Jquery 框架。特点:

  • 易用 html css javascript
  • 高效 开发前端页面 非常高效
  • 灵活 开发灵活 多样性

MVVM(Model-View-ViewModel)是一种软件架构设计模式,MVVM 源自于经典的 MVC(Model-View-Controller)模式;MVVM 的核心是 ViewModel 层,负责转换 Model 中的数据对象来让数据变得更容易管理和使用,其作用如下:

  • 该层向上与视图层进行双向数据绑定
  • 向下与 Model 层通过接口请求进行数据交互

View

View 是视图层,也就是用户界面。前端主要由 HTMLCSS 来构建,为了更方便地展现 ViewModel 或者 Model 层的数据,已经产生了各种各样的前后端模板语言,比如 FreeMarker、Thymeleaf 等等

Model

Model 是指数据模型,泛指后端进行的各种业务逻辑处理和数据操控,主要围绕数据库系统展开。这里的难点主要在于需要和前端约定统一的 接口规则

ViewModel

ViewModel 是由前端开发人员组织生成和维护的视图数据层。在这一层,前端开发者对从后端获取的 Model 数据进行转换处理,做二次封装,以生成符合 View 层使用预期的视图数据模型。

2.2 实例

2.2.1 入门示例

  1. <!DOCTYPE html>
  2. <html lang="en">
  3. <head>
  4. <meta charset="UTF-8">
  5. <title>Vue 入门</title>
  6. </head>
  7. <body>
  8. <div id="app">
  9. <span> I am {{name}} ! </span>
  10. <br>
  11. <span>
  12. {{ msg }} <!--{{}}:插值表达式-->
  13. </span>
  14. </div>
  15. <!-- 开发环境版本,包含了有帮助的命令行警告 -->
  16. <script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
  17. <!-- 生产环境版本,优化了尺寸和速度 -->
  18. <script src="https://cdn.jsdelivr.net/npm/vue"></script>
  19. <script>
  20. const app = new Vue({
  21. el : "#app", // element 用来给 Vue 实例定义一个作用范围
  22. data : { // 用来给 Vue 定义一些相关数据
  23. msg : "Hello Vue.js !",
  24. name : "zhenyu"
  25. }
  26. });
  27. </script>
  28. </body>
  29. </html>
  • Vue 实例对象中 el 属性:代表 Vue 的作用范围,在 Vue 的作用范围内都可以使用 Vue 的语法。
  • Vue 实例对象中 data 属性:用来给 Vue 实例绑定一些相关数据,绑定的数据可以通过 {{ xx }} 在 Vue 作用范围内取出。
  • 在使用 {{ xx }} 进行获取 data 中数据时,可以在 {{ }}中书写表达式、运算符、调用相关方法以及逻辑运算等。
  • el 属性中可以书写任意的 CSS选择器[jquery选择器],但是在使用 Vue 开发推荐使用 id选择器

2.3 基础语法

2.3.1 v-text:

v-text:用来获取 data 中数据将数据以文本的形式渲染到指定标签内部,类似于 javascript 中 innerText

{{ xx }}(插值表达式)和 v-text 获取数据的区别在于:

  • 使用 v-text 取值会将标签中原有的数据覆盖
    插值表达式的形式不会覆盖标签原有的数据。
  • 使用 v-text 可以避免在网络环境较差的情况下出现插值闪烁。(已修复)

2.3.2 v-html:

v-html:用来获取 data 中数据将数据中含有的 html 标签先解析在渲染到指定标签的内部,类似于 javascript 中 innerHTML

2.3.3 v-on:

v-on:事件绑定

  • v-on:click 可以简化成 @click
  • 事件函数可以简写,dowork: function() {} 可以简写成 dowork() {}

2.3.4 v-show:

v-show:用来控制页面中某个标签元素是否展示,底层通过控制元素的 display 属性来进行标签的显示和不显示控制。

  • v-show 中可以直接书写 boolean 值控制元素展示
  • v-show 中可以通过 变量 控制标签展示和隐藏。
  • v-show 中可以通过 boolean表达式 控制标签的展示和隐藏。

2.3.5 v-if:

v-if:用来控制页面中的标签元素是否展示,底层通过对 dom 树节点进行添加和删除来控制展示和隐藏。

v-show 的用法一模一样,参考 v-show 即可。

2.3.6 v-bind:

v-bind:用来绑定 标签的属性 从而通过 vue 动态修改标签的属性。

  • v-bind : 属性 可以简写成 : 属性

2.3.7 v-for:

v-for:用来对 对象 进行遍历的(JavaScript 中数组也是对象的一种)

  • 在使用 v-for 的时候一定要注意加入:key 用来给 Vue 内部提供重用和排序的唯一 key
  • 遍历时可以获取 索引 index、…

2.3.8 v-model:

v-model:用来绑定 标签元素的值vue实例对象中data数据 保持一致,从而实现 双向的数据绑定机制

  • 所谓双向绑定,就是表单中数据变化导致 vue 实例 data 数据变化,vue 实例中 data 数据的变化导致表单中数据变化。

2.3.9 记事本案例

<!DOCTYPE html>
<html lang="en" xmlns:v-on="http://www.w3.org/1999/xhtml">

<head>
  <meta charset="UTF-8">
  <title>记事本综合案例</title>
</head>

<body>
  <div id="app">
    <input type="text" v-model="msg">
    <input type="button" value="添加到记事本" @click="save"><br><br>
    【记事本内容】:
    <ul v-for="item,index in lists">
      <li>
        {{ index + 1}} : {{ item }} <a href="javascript:;" @click="delRow(index)">删除</a>
      </li>
    </ul>
    <br>
    <span>总数量: {{ lists.length }} 条</span>
    <input type="button" v-show="lists.length != 0" value="删除所有" @click="deleteAll">
  </div>

  <!--
     1.完成记事本的查询所有思路: 
      1).将所有数据绑定为vue实例 
      2).遍历vue实例中数据到页面
    2.添加 
      1).添加按钮绑定事件中 
      2).在事件中获取输入框中数据 
      3).将获取的数据放入到lists里面
     1.完成记事本的查询所有思路: 
      1).将所有数据绑定为vue实例 
      2).遍历vue实例中数据到页面
    2.添加 
      1).添加按钮绑定事件中 
      2).在事件中获取输入框中数据 
      3).将获取的数据放入到lists里面
    3.删除  
      1).删除所有  
      2).总数量
    -->
  <script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
  <script>
    const app = new Vue({
      el: "#app",
      data: {
        lists: ["这是一个记事本的小案例!"],
        msg: ''
      },
      methods: {
        save() {
          this.lists.push(this.msg)
          this.msg = ''
        },
        delRow(index) { // 删除一条记录
          // 根据下标删除数组中某个元素
          this.lists.splice(index)
        },
        deleteAll() { // 删除所有数据
          this.lists = []
        },
      },
    });
  </script>
</body>
</html>

2.3.10 修饰符

(1)事件修饰符

修饰符作用:用来和事件连用,决定事件触发条件或者是阻止事件的触发机制。

常用的事件修饰符:

  • .stop:用来阻止事件冒泡。
  • .prevent:用来阻止标签的默认行为。
  • .capture
  • .self:只触发自己标签的上特定动作的事件,不监听事件冒泡。
  • .once:让指定事件只触发一次。
  • .passive

(2)按键修饰符

作用:用来与键盘中按键事件绑定在一起,用来修饰特定的按键事件的修饰符。

常用按键修饰符:@keyup.xxx="function "

2.4 Axios异步通信

中文网站:https://www.kancloud.cn/yunye/axios/234845

2.4.1 执行 GET 请求

// 为给定 ID 的 user 创建请求
axios.get('/user?ID=12345')
  .then(function (response) {
    console.log(response);
  })
  .catch(function (error) {
    console.log(error);
  });

// 可选地,上面的请求可以这样做
axios.get('/user', {
    params: {
      ID: 12345
    }
  })
  .then(function (response) {
    console.log(response);
  })
  .catch(function (error) {
    console.log(error);
  });

2.4.2 执行 POST 请求

axios.post('/user', {
    firstName: 'Fred',
    lastName: 'Flintstone'
  })
  .then(function (response) {
    console.log(response);
  })
  .catch(function (error) {
    console.log(error);
  });

2.4.3 执行多个并发请求

function getUserAccount() {
  return axios.get('/user/12345');
}

function getUserPermissions() {
  return axios.get('/user/12345/permissions');
}vue

axios.all([getUserAccount(), getUserPermissions()])
  .then(axios.spread(function (acct, perms) {
    // 两个请求现在都执行完成
  }));

2.5 生命周期

<!DOCTYPE html>
<html lang="en" xmlns:v-on="http://www.w3.org/1999/xhtml">

<head>
  <meta charset="UTF-8">
  <title>vue生命周期函数</title>
</head>

<body>
  <div id="app">
    <span id="sp"> {{ msg }} </span>
    <input type="button" value="改变data的值" @click="changeData">
  </div>
  <!-- 引入Vue  -->
  <script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
  <script>
    const app = new Vue({
      el: "#app",
      data: {
        msg: "hello Vue.js!",
      },
      methods: {
        changeData() {
          // this.msg = "Vue.js niubility!";
          this.msg = Math.random();
        }
      },
      // ====================初始化阶段====================
      // 1.生命周期中第一个函数,该函数在执行时Vue实例仅仅完成了自身事件的绑定和生命周期函数的初始化工作,Vue实例中还没有 Data el methods相关属性
      beforeCreate() {
        console.log("beforeCreate: " + this.msg);
      },
      // 2.生命周期中第二个函数,该函数在执行时Vue实例已经初始化了data属性和methods中相关方法
      created() {
        console.log("created:" + this.msg);
      },
      // 3.生命周期中第三个函数,该函数在执行时Vue将El中指定作用范围作为模板编译
      beforeMount() {
        console.log("beforeMount: " + document.getElementById("sp").innerText);
      },
      // 4.生命周期中第四个函数,该函数在执行过程中,已经将数据渲染到界面中并且已经更新页面
      mounted() {
        console.log("Mounted: " + document.getElementById("sp").innerText);
      },
      // ====================运行阶段====================
      // 5.生命周期中第五个函数,该函数是data中数据发生变化时执行 这个事件执行时仅仅是Vue实例中data数据变化页面显示的依然是原始数据
      beforeUpdate() {
        console.log("beforeUpdate-vue: " + this.msg);
        console.log("beforeUpdate-dom: " + document.getElementById("sp").innerText);
      },
      // 6.生命周期中第六个函数,该函数执行时data中数据发生变化,页面中数据也发生了变化  页面中数据已经和data中数据一致
      updated() {
        console.log("updated-vue: " + this.msg);
        console.log("updated-dom: " + document.getElementById("sp").innerText);
      },
      // ====================销毁阶段====================
      // 7.生命周期第七个函数,该函数执行时,Vue中所有数据 methods componet 都没销毁
      beforeDestory() { },
      // 8.生命周期的第八个函数,该函数执行时,Vue实例彻底销毁
      destoryed() { }
    });
  </script>
</body>
</html>

2.6 组件

在实际开发中,并不会用以下方式开发组件,而是采用vue-cli创建,vue模板文件的方式开发,以下方法只是为了让大家理解什么是组件。组件是可复用的Vue实例, 说白了就是一组可以重复使用的模板。

<!DOCTYPE html>
<html>
<head>
  <meta charset='utf-8'>
  <title>局部组件的开发</title>
</head>
<body>
  <div id="app">
    <login></login>
    <login></login>
    <login></login>
  </div>
  <script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
  <script>
    // 定义变量用来保存模板配置对象
    const login = {
      template: '<div><h2>用户登录</h2></div>'
    };
    const app = new Vue({
      el: "#app",
      data: {},
      methods: {},
      components: { // 局部组件
        login: login // 注册局部组件
      }
    });
  </script>
</body>
</html>

2.7 计算属性

计算属性的重点突出在属性两个字上(属性是名词),首先它是个属性其次这个属性有计算的能力(计算是动词),这里的计算就是个函数,计算属性的主要特性就是为了将不经常变化的计算结果进行缓存,以节约我们的系统开销;

<script type="text/javascript">
    var vm = new Vue({
        el:"#app",
        data:{
          message:"pan"
        },
        methods:{
            currentTime1:function(){
                return Date.now();//返回一个时间戳
            }
        },
        computed:{
            currentTime2:function(){//计算属性:methods,computed方法名不能重名,重名之后,只会调用methods的方法
                this.message;
                return Date.now();//返回一个时间戳
            }
        }
    });
</script>

2.8 路由

定义一个Content.vue 的组件

<template>
    <div>
        <h1>内容页</h1>
    </div>
</template>

<script>
    export default {
        name:"Content"
    }
</script>

Main.vue组件

    <template>
    <div>
        <h1>首页</h1>
    </div>
</template>

<script>
    export default {
        name:"Main"
    }
</script>

安装路由,在src目录下,新建一个文件夹:router,专门存放路由,配置路由index.js,如下

import Vue from'vue'
//导入路由插件
import Router from 'vue-router'
//导入上面定义的组件
import Content from '../components/Content'
import Main from '../components/Main'
//安装路由
Vue.use(Router) ;
//配置路由
export default new Router({
    routes:[
        {
            //路由路径
            path:'/content',
            //路由名称
            name:'content',
            //跳转到组件
            component:Content
            },{
            //路由路径
            path:'/main',
            //路由名称
            name:'main',
            //跳转到组件
            component:Mian
            }
        ]
    });

main.js中配置路由

import Vue from 'vue'
import App from './App'

//导入上面创建的路由配置目录
import router from './router'//自动扫描里面的路由配置

//来关闭生产模式下给出的提示
Vue.config.productionTip = false;

new Vue({
    el:"#app",
    //配置路由
    router,
    components:{App},
    template:'<App/>'
});

3.Vue CLI

3.1 简介

Vue CLI 是一个基于 Vue.js 进行快速开发的完整系统。使用 Vue 脚手架之后我们开发的页面将是一个完整系统(项目)。官方网站:https://cli.vuejs.org/zh/guide/

Vue CLI 中项目开发方式:一切皆组件!

VueCLI 开发方式是在项目中开发一个一个组件对应一个业务功能模块,日后可以将多个组件组合到一起形成一个前端系统。

日后在使用 Vue CLI 进行开发时不再书写html,编写的是一个个组件(.vue文件),打包时 Vue CLI 会将组件编译成运行的 html 文件。

3.2 第一个 Vue 脚手架项目

3.2.1 命令创建项目

(1)使用以下命令来创建一个新项目:
vue create hello-world

(2)我们选择 手动配置:用方向键 ↑ ↓ 操控选项,Enter 确定;
Please pick a preset: (Use arrow keys)
> default (babel, eslint) # 默认配置
  Manually select features # 手动配置
123

(3)选择配置,勾选如下即可:方向键 ↑ ↓ 操作,按空格选中,Enter 确定;
Vue CLI v4.4.6
Please pick a preset: Manually select features
Check the features needed for your project:
 (*) Babel
 ( ) TypeScript
 ( ) Progressive Web App (PWA) Support
 (*) Router
 (*) Vuex
 (*) CSS Pre-processors
 (*) Linter / Formatter
 ( ) Unit Testing
>( ) E2E Testing
123456789101112

(4)首先检查刚才选择的配置;

然后问我们是否使用 history mode,其实就是页面路由含不含有 #;这里我们选择 Y

Check the features needed for your project: Babel, Router, Vuex, CSS Pre-processors, Linter
Use history mode for router? (Requires proper server setup for index fallback in production) (Y/n) 
y
123

(5)选择CSS预编译器,这里我们选择Less;
Pick a CSS pre-processor (PostCSS, Autoprefixer and CSS Modules are supported by default): (Use arrow keys)
> Sass/SCSS (with dart-sass)
  Sass/SCSS (with node-sass)
  Less
  Stylus
12345

(6)选择 ESLint 代码校验规则,

提供一个插件化的 javascript 代码检测工具,这里我们选择 ESLint + Prettier;

Pick a linter / formatter config:
  ESLint with error prevention only
  ESLint + Airbnb config
  ESLint + Standard config
> ESLint + Prettier
12345

(7)选择什么时候进行代码校验,Lint on save:保存就检查,

Lint and fix on commit:fix 或者 commit 的时候检查,这里我们选择第一个;

Pick additional lint features: (Press <space> to select, <a> to toggle all, <i> to invert selection)
>(*) Lint on save
 ( ) Lint and fix on commit
123

(8)选择把配置保存到哪个文件中,

In dedicated config files 存放到独立文件中,In package.json 存放到 package.json 中,
这里我们选择放到 package.json 中;

Where do you prefer placing config for Babel, ESLint, etc.? (Use arrow keys)
  In dedicated config files
> In package.json
123

(9)问我们是否保存刚才的配置,以后的文件可以直接使用,选择 N。
Save this as a preset for future projects? (y/N)
N
12

(10)使用如下命令运行项目:
cd hello-world # 首先进入项目根路径

npm run serve # 运行项目

(11)浏览器输入如下路径来访问项目:
http://localhost:8080

3.2.2 图形化界面创建项目

使用图形化界面创建和管理项目:

vue ui

VUE - 图1

  • node_modules:用于存放我们项目的各种依赖;
  • public:用于存放静态资源(不会变动的);
    • public/index.html:模板文件,作用是生成项目的入口文件。
      浏览器访问项目的时候就会默认打开的是生成好的 index.html。
  • src:是存放各种 .vue 文件的地方。
    • src/assets:用于存放着各种静态文件(可能会变动),比如图片。
    • src/components:存放公共组件(可复用),比如 header.vue、footer.vue 等。
    • src/router/index.js:vue-router 路由文件。
      需要引入 src/views 文件夹下的 .vue,配置 path、name、component。
    • src/store/index.js:是 vuex 的文件,主要用于项目里边的一些状态保存。
      比如 state、mutations、actions、getters、modules。
    • src/views,存放页面组件(不可复用),比如 Login.vue,Home.vue。
    • src/App.vue:App.vue 是项目的主组件;
      App.vue 中使用 router-link 引入其他模块,所有的页面都是在 App.vue 下切换的。
    • src/main.js:入口文件,主要作用是初始化 vue 实例,同时可以在此文件中引用某些组件库或者全局挂载一些变量。
  • .gitignore:配置 git 上传想要忽略的文件格式。
  • babel.config.js:一个工具链,主要用于在当前和较旧的浏览器或环境中将 ES6 的代码转换向后兼容(低版本ES)。
  • package.json:模块基本信息项目开发所需要的模块,版本,项目名称。
  • package-lock.json:是在 npm install 时候生成的一份文件,用于记录当前状态下实际安装的各个 npm package 的具体来源和版本号

3.2.3 vue-cli 中使用 Axios

(1)安装 axios
npm install axios --save-dev

(2)配置文件 main.js 中引入 axios:
import axios from 'axios';
Vue.prototype.$http=axios;

(3)使用 axios:
this.$http.get("url").then((res)=>{});
this.$http.post("url").then((res)=>{});

3.2.4 Vue 脚手架项目部署到 springboot 项目

打包完后,如何将项目部署到 SpringBoot 项目上呢?

将打包好的 dist 目录放到 SpringBoot 项目的 static 目录下;

由于我在配置文件中配置了项目路径:(没有访问路径则不需要修改)

server.servlet.context-path=/vue

所以要修改一下 index.html 中引入资源文件的路径;

通过以下路径访问部署的前端页面:

http://localhost:8989/vue/dist/index.html

4.Element UI

4.1介绍与安装

4.1.1 介绍

官网:https://element.eleme.io/#/zh-CN

官方定义:网站快速成型工具桌面端组件库;Element UI 中提供的全部都是封装好组件。

4.1.2 安装

  • 首先通过 Vue脚手架 创建项目:
vue create hello-element
1
  • 在 Vue 脚手架项目中安装 Element UI:
npm i element-ui -S
1
  • 指定项目中使用 Element UI,在 index.js 中添加以下代码:`
import ElementUI from 'element-ui';
import 'element-ui/lib/theme-chalk/index.css';

Vue.use(ElementUI); // 在vue脚手架中使用elementui

4.1.2 使用

每个组件都有 属性、事件、方法。事件和方法的区别在于:事件是去调用自己写的函数,方法相当于它给你写好的函数,你去调用;

掌握 属性、事件、方法 的用法后,所有组件的使用基本都一样。

  • 大部分组件都是以 el-组件名 开头,比如 el-button 是按钮;
<el-button>默认按钮</el-button>
1
  • Element UI 中所有组件的 属性(Attributes) 全部写在组件标签上;
<el-button type="primary" 属性名=属性值>默认按钮</el-button>
1
  • 事件(Events) 也是直接写在对应的组件标签上,使用 Vue 中绑定事件方式 @change="aa"
<el-radio v-model="label" @change="aa" name="sex" label="男">男</el-radio>
<el-radio v-model="label" @change="aa" name="sex" border size="small" label="女">女</el-radio>

<script>
    export default {
        name: "Radio",
        data(){
            return{
                label:'男'
            }
        },
        methods:{
            aa(){ //定义的事件处理函数
                console.log(this.label);
            }
        }
    }
</script>
123456789101112131415161718
  • 组件的 方法(Methods)
    在对应的组件中加入 ref="组件别名"
    通过 this.$refs.组件别名.方法名() 调用方法;
<h1>方法的使用</h1>
<el-input v-model="username" ref="inputs"></el-input>

<el-button @click="focusInputs">focus方法</el-button>
<el-button @click="blurInputs">blur方法</el-button>

<script>
    export default {
        name: "Input",
        data() {
            return{}
        },
        methods:{
            // 调用focus方法
            focusInputs(){
                this.$refs.inputs.focus();
            },
           // 调用失去焦点方法
            blurInputs(){
                this.$refs.inputs.blur();
            }
        }
    }
</script>