精华内容
下载资源
问答
  • 千锋网站的底部也终于完工,在调整ul>li里面的span和a的距离时,可以把他俩display:block,转换成行内块元素,再调整他俩的padding-top和padding-bottom值。二维码直接用positive做的,给父级一个positive:...

    一早上都在跟着做导航栏,虽然看着不咋样,但是确实挺拉跨,反正能做出来效果就行了!在这里插入图片描述
    在这里插入图片描述
    在这里插入图片描述
    在这里插入图片描述
    然后!千锋网站的底部也终于完工,在调整ul>li里面的span和a的距离时,可以把他俩display:block,转换成行内块元素,再调整他俩的padding-top和padding-bottom值。二维码直接用positive做的,给父级一个positive:relative,给寄几一个position:absolute;top:15px ;right=15px
    在这里插入图片描述

    做完了看起来就感觉整挺好
    然后👴继续开始整品优购,品优购不愧是品优购,PS都让我电脑重启了两次。加了左边的导航栏,中间的banner,右边的表格写起来有点费劲明天写,还要加字体图标。

    在这里插入图片描述
    消除浮动是怎么个意思。

    展开全文
  • 千锋网络安全渗透测试Web架构安全分析章节配套的一个网站源码(cms.zip),用于安全渗透学习,名称为:文章管理系统。使用前需要先配置数据库,导入mysql文件。 这个网站仅用于千锋网络安全学习使用,内容来源网络,...
  • 千锋逆战班学习第51天Servlet概念Servlet三种方式实现Servlet的生命周期load on startup配置Servlet配置缺省Servlet服务器中路径问题ServletConfig对象ServletContext对象站点访问次数案例 千锋逆战班学习第51天 ...


    千锋逆战班学习第51天
    努力或许没有收获,但不努力一定没收获,加油。
    今天我学习了Servlet。

    Servlet概念

    A_概念

    在这里插入图片描述

    HttpServlet继承于GenericServlet、GenericServlet实现于Servlet,也就是说Servlet是顶层接口!!!

    如果要实现Servlet功能,有几种方式?

    方式一:实现Servlet接口

    在servlet接口中,没有doGet和doPost方法,处理请求是service方法(抽象的)
    

    方式二:继承GenericServlet类

    在GenericServlet类中,没有doGet和doPost方法,处理请求是service方法(抽象的)
    

    方式三:继承HttpServlet类

    猜想,HttpServlet类中重写service方法。
    
    根据源码,发现重写service方法中,
    
    有将ServletRequest强转为HttpServletRequest, 
    
    将ServletResponse强转为HttpServletResponse
    
    以上强转是因为,ServletRequest和ServletResponse并没有针对Http协议做优化!!!无法专门针对http协议调用方法!!
    
    HttpServletRequest和HttpServletResponse有针对http协议做优化!!!
    

    B_总结

    以上三种方式,推荐使用哪一种?为什么?
    
    推荐使用继承HttpServlet类,针对http协议有优化!!!
    

    Servlet三种方式实现

    A_继承HttpServlet

    在HttpServlet中,重写GenricServlet类中的service方法,会由GenericServlet给service方法提供请求对象(ServletRequest)、响应对象(ServletResponse),不针对Http协议!!所以需要强转成HttpServletRequest、HttpServletResponse。
    
    紧接着,调用另外一个service方法,传入HttpServletRequest、HttpServletResponse
    
    获取到请求方式,如果是get请求,就调用doGet方法,如果是post请求,就调用doPost方法!!
    

    B_继承GenericServlet类

    如果要针对Http协议,需要手动强转
    

    C_实现Servlet接口

    如果要针对Http协议,需要手动强转
    

    Servlet的生命周期

    A_Servlet源码

    public interface Servlet {
        void init(ServletConfig var1) throws ServletException;
    
        ServletConfig getServletConfig();
    
        void service(ServletRequest var1, ServletResponse var2) throws ServletException, IOException;
    
        String getServletInfo();
    
        void destroy();
    }
    
    
    
    init(ServletConfig var1):
    
    	监听Servlet的初始化
    
    service(ServletRequest var1, ServletResponse var2):
    
    	处理请求
    
    destroy():
    
    	监听Servlet的销毁
    

    B_生命周期

    一个事物,从开始、存活、结束!说白了,就是需要看Servlet的初始化、存活、销毁!!
    

    C_Servlet的生命周期特点

    servlet什么时候初始化?
    
    	Servlet默认不是随着服务器的启动而初始化,当第一次访问Servlet时才初始化,后面访问就执行处理请求
    
    	会发现Servlet是一个单例!!
    
    servlet什么时候销毁?
    
    	服务器关闭的时候会销毁Servlet
    

    load on startup配置

    A_概念
    
    	根据Servlet生命周期,可知,servlet默认不会随着服务器的启动而初始化!
    
    	如果,就想让指定的Servlet跟随服务器启动而初始化,我们如何做?需要用到load on startup
    
    	load on startup可以让servlet随着服务器的启动而初始化
    
    B_load on startup
    
    	有10个优先级:1~10;数字越小,优先级越高!
    
    	比如:Demo01Servlet,load-on-startup:1 ;Demo02Servlet , load-on-startup :2;
    
    	当服务器启动时,Demo01Servlet先初始化,然后,Demo02Servlet再初始化!
    
     <servlet>
         <servlet-name>Demo05Servlet</servlet-name>
         <servlet-class>com.qfedu.servlet.Demo05Servlet</servlet-class>
         <load-on-startup>3</load-on-startup>
     </servlet>
     <servlet-mapping>
         <servlet-name>Demo05Servlet</servlet-name>
         <url-pattern>/demo05</url-pattern>
     </servlet-mapping>
    

    Servlet配置

    A_概念

    自定义Servlet,第一步,声明该Servlet;第二步,给该Servlet配置访问路径
    

    B_问题一

    一个Servlet是否可以有多个访问名称?
    
    可以有多个访问名称,只需要给对应的Servlet多个<servlet-mapping>标签即可!
    

    C_问题二

    <url-parttern>书写规则
    
    完全匹配:
    
    	要求网址上的访问名称完全和<url-parttern>一致
    
    	必须以"/"开头,否则会报错:IllegalArgumentException : Invalid <url-pattern> 
    
    目录匹配:
    
    	要求网址上的访问名称中的目录和<url-parttern>一致
    
    	必须以"/"开头,以"*"结尾
    
    	比如:/a/b/* , 目录必须是/a/b,后面随便写
    
    后缀名匹配:
    
    	要求网址上的访问名称中的后缀和<url-parttern>一致
    
    	不能以"/"开头,以"*"开头,后缀名根据业务写
    
    	比如:*.xyz。后缀名必须是xyz,其他随意写!!!
    

    缺省Servlet

    • A_概念
      url-parttern的值为"/"就是缺省Servlet
    • B_作用
      tomcat容器自带缺省Servlet
      处理匹配不到的资源,返回404页面
      处理静态资源,io流读写
    • C_自定义缺省Servlet
      在当前工程中自定义Servlet,将url-parttern设置为"/",就覆盖了tomcat容器中的缺省Servlet
    • D_应用
      SpringMVC框架中,用于放行静态资源!

    服务器中路径问题

    • 路径分类
      带协议的绝对路径:http://localhost:8080/day51/img/girl.jpg
      不带协议的绝对路径:/day51/img/girl.jpg
      相对路径:
      当前目录:./ ,可以省略
      上一级目录:…/
    • 总结
      开发中,用的比较多:不带协议的绝对路径、相对路径

    ServletConfig对象

    • 概述
      ServletConfig是由tomcat容器创建,通过init方法传入给Servlet
    • 作用
      • 获取Servlet的名称标签内容

      • 获取Servlet的初始化参数

        • 随着Servlet的初始化而初始化

          Demo11Servlet
          com.qfedu.servlet.Demo11Servlet


          username
          root


          password
          root123


          getInitParameter(String parameterName):根据参数名称获取指定的参数值
          getInitParameterNames():获取所有的参数名称
      • 获取域对象:ServletContext

    ServletContext对象

    • 概述
      • 相当于是整个应用程序对象
    • 作用
      • ServletContext是一个域对象,可以用来存储数据
        • 在应用程序中的任何位置都能够访问
        • getAttribute(String parameterName) : 获取ServletContext域中指定名称的参数值
        • setAttribute(String paramterName,Object parameterValue):存储参数到ServletContext域中
        • removeAttribute(String parameterNam):将ServletContext域中指定名称的参数移除!
      • 获取全局初始化参数
        • 会随着服务器的启动而初始化
        • getInitParameter(String parameterName):根据参数名称获取指定的参数值
        • getInitParameterNames():获取所有的参数名称

          username
          root456
      • 获取服务器真实磁盘路径
        • getRealPath:依据当前项目去生成真实磁盘路径(在通过getRealPath()方法获取的字符串后加上当前目录),
          比如:servletContext.getRealPath(“upload”)
          “当前项目的服务器磁盘路径/upload”
          比如:servletContext.getRealPath(“upload/img”):
          “当前项目的服务器磁盘路径/upload/img”

    站点访问次数案例

    • 使用ServletContext域对象
    • 步骤
      • 判断是否是第一次请求
        Integer count = servletContext.getAttribute(“count”);
        if(count == null){

        } else {

        }

      • 如果是第一次请求
        int count = 1;
        System.out.println("访问次数 : " + count);
        servlet.setAttribute(“count”,count);

      • 如果不是第一次请求
        count++;
        System.out.println("访问次数 : " + count);
        servlet.setAttribute(“count”,count);

    Servlet3.0

    • 概念
      Servlet2.5,不支持注解开发。
      Servlet3.0,支持注解开发。
    • 常用注解
      @Test:单元测试
      @Override:方法重写
    • @WebServlet:
      • 声明配置Servlet,取代了web.xml配置
        @WebServlet(name = “Demo18Servlet”,urlPatterns = “/demo18”)
        public class Demo18Servlet extends HttpServlet {

        }
        以上配置代码,相当于web.xml配置如下:

        Demo18Servlet
        com.qfedu.servlet.Demo18Servlet


        Demo18Servlet
        /demo18

    展开全文
  • 千锋教育的开源教育视频(哔哩哔哩视频网站千锋官方入驻): https://space.bilibili.com/146668655 食用视频教程时,可以参见如下文本教程: 菜鸟教程的python3教程:...
  • 千锋 Vue 详细笔记整理

    千次阅读 多人点赞 2021-12-11 22:06:09
    视频笔记是根据B站 千锋 涛哥 - SpringBoot+vue+前后端分离项目《锋迷商城》实战课-完结版 进行整理的 笔记可上 gitee仓库 自取 千锋 Vue 笔记整理 一、vue 的简介 1.1 使用 JQuery 的复杂性问题 1.2 VUE 简介 1.2.1...

    视频笔记是根据B站 千锋 涛哥 - SpringBoot+vue+前后端分离项目《锋迷商城》实战课-完结版 进行整理的

    笔记可上 gitee仓库 自取

    千锋 Vue 笔记整理

    一、vue 的简介

    在这里插入图片描述

    1.1 使用 JQuery 的复杂性问题

    • 使用 JQuery 进行前后端分离开发,既可以实现前后端交互 (ajax) ,又可以完成数据渲染
    • 存在的问题: JQuery 需要通过 HTML 标签拼接、DOM 节点操作完成数据的显示,开发效率低且容易出错,渲染效率较低
    • vue 是继 JQuery 之后的又一优秀的前端框架:专注于前端数据的渲染 ———— 语法简单、渲染效率高

    1.2 VUE 简介

    1.2.1 前端框架

    • 前端三框架:HTML、CSS、JavaScript

      • HTML 决定网页结构
      • CSS 决定显示效果
      • JavaScript 决定网页功能 (交互、数据显示)
    • UI 框架:(只提供样式、显示效果)

      • Bootstrap
      • amazeUI
      • Layui
    • JS 框架:

      • JQuery (JQuery UI)
      • React
      • angular
      • nodejs ---- 后端开发
      • vue 集各种前端框架的优势发展而来

    1.2.2 MVVM

    项目结构经历的三个阶段:

    后端 MVC :可以理解为单体结构,流程控制是由后端控制器来完成

    前端 MVC :前后端分离开发,后端只负责接收响应请求

    MVVM是MVC的增强版,实质上和MVC没有本质区别,只是代码的位置变动而已

    MVVM 前端请求后端接口,后端返回数据,前端接收数据,并将接收到的数据设置为 “VM”,HTML 从 vm 取值

    • M model 数据模型,指的是后端接口返回的数据
    • V view 视图
    • VM ViewModel 视图模型 数据模型与视图之间的桥梁,后端返回的 model 转换前端所需的 vm,视图层可以直接从 vm 中提取数据

    在这里插入图片描述

    Model-View-ViewModel —— 概念图

    二、 vue 入门使用

    Vue (读音 /vjuː/,类似于 view) 是一套用于构建用户界面的渐进式框架。与其它大型框架不同的是,Vue 被设计为可以自底向上逐层应用。Vue 的核心库只关注视图层,不仅易于上手,还便于与第三方库或既有项目整合。另一方面,当与现代化的工具链以及各种支持类库结合使用时,Vue 也完全能够为复杂的单页应用提供驱动。

    2.1 vue 的引入

    • 离线引用:下载 vue 的 js 文件,添加到前端项目,在网页中通过 script 标签引用 vue.js 文件

    • CDN 引用:

      直接使用在线 CDN 的方式引入

    <!-- 开发环境版本,包含了有帮助的命令行警告 -->
    <script src="https://cdn.jsdelivr.net/npm/vue@2/dist/vue.js"></script>
    

    2.2 入门案例 – Hello World

    文本:数据绑定最常见的形式就是使用“Mustache”语法 (双大括号) 的文本插值:{{message}}

    1. 创建一个 HTML 文件

    2. 引入 vue.js 文件

      <script src="https://cdn.jsdelivr.net/npm/vue@2/dist/vue.js"></script>
      
    3. 示例:

    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>Title</title>
        <!-- 引入vue.js-->
        <script src="https://cdn.jsdelivr.net/npm/vue@2/dist/vue.js"></script>
    </head>
    <body>
        <div id="app-1">
            从 0 开始: {{message}}
        </div>
    
    
        <script type="text/javascript">
            var vm = new Vue({
                el: '#app-1',
                data: {
                    message: 'Hello World!'
                }
            })
    
        </script>
    </body>
    </html>
    

    在这里插入图片描述

    Mustache 标签将会被替代为对应数据对象上 message property 的值。无论何时,绑定的数据对象上 message property 发生了改变,插值处的内容都会更新。

    三、 vue 的语法

    3.1 基本类型数据和字符串

    <div id="app-2">
        {{code}}
        从 0 开始: {{message}}
    </div>
    
    
    <script type="text/javascript">
        var vm = new Vue({
            el: '#app-2',
            data: {
                code: 1_3_3,
                message: 'Hello World!'
            }
        })
    
    </script>
    

    在这里插入图片描述

    3.2 对象类型数据

    • 支持 ognl 语法
    <div id="app-3">
        学号:{{stu.stuNum}} <br />
        姓名:{{stu.stuName}} <br />
        性别:{{stu.stuGender}} <br />
        年龄:{{stu.stuAge}}
    </div>
    
    <script type="text/javascript">
        var vm = new Vue({
            el: '#app-3',
            data: {
                stu: {
                    stuNum: '10001',
                    stuName: '张三',
                    stuGender: 'M',
                    stuAge: 20
                }
            }
        })
    
    </script>
    

    在这里插入图片描述

    3.3 条件 v-if

    v-if : 用来控制切换一个元素是否显示 (底层控制是 DOM 元素,操作 DOM)

    注:在浏览器中网页打开这个文件 F12,从标签上可以看到没有 stu.stuGender == 'F' 对应的元素。即条件不成立,网页不会渲染该 DOM,连标签都不会有。

    <div id="app-4">
        学号:{{stu.stuNum}} <br />
        姓名:{{stu.stuName}} <br />
        性别:
        <label v-if="stu.stuGender == 'M'"></label>
        <label v-if="stu.stuGender == 'F'"></label>
        <br />
        年龄:{{stu.stuAge}}
    
    </div>
    
    <script type="text/javascript">
        var vm = new Vue({
            el: '#app-4',
            data: {
                stu: {
                    stuNum: '10001',
                    stuName: '张三',
                    stuGender: 'M',
                    stuAge: 20
                }
            }
        })
    
    </script>
    

    在这里插入图片描述

    3.4 循环 v-for

    v-for 指令基于一个数组来渲染一个列表。

    v-for 块中,我们可以访问所有父作用域的 property。v-for 还支持一个可选的第二个参数,即当前项的索引。

    <div id="app-5">
        <table border="1" cellspacing="0" width="400">
            <tr>
                <th>序号</th>
                <th>学号</th>
                <th>姓名</th>
                <th>性别</th>
                <th>年龄</th>
            </tr>
            <tr v-for="(stu, index) in stus">
                <td>{{index + 1}}</td>
                <td>{{stu.stuNum}}</td>
                <td>{{stu.stuName}}</td>
                <td>
                    <table v-if="stu.stuGender == 'M'"></table>
                    <table v-if="stu.stuGender == 'F'"></table>
                </td>
                <td>{{stu.stuAge}}</td>
    
            </tr>
        </table>
    
    </div>
    
    <script type="text/javascript">
        var vm = new Vue({
            el: '#app-5',
            data: {
                stus: [
                    {
                        stuNum: '10001',
                        stuName: '张三',
                        stuGender: 'M',
                        stuAge: 20
                    },
                    {
                        stuNum: '10002',
                        stuName: '李四',
                        stuGender: 'M',
                        stuAge: 23
                    },
                    {
                        stuNum: '10003',
                        stuName: '郑红',
                        stuGender: 'F',
                        stuAge: 19
                    }
                ]
            }
        })
    
    </script>
    

    在这里插入图片描述

    3.5 绑定标签属性 v-bind

    • v-bind:属性名 缩写:属性名
    <div id="app-6">
        <input type="text" v-bind:value="message">
        <hr /><br />
        <table border="1" cellspacing="0" width="400">
            <tr>
                <th>序号</th>
                <th>学号</th>
                <th>姓名</th>
                <th>性别</th>
                <th>年龄</th>
            </tr>
            <tr v-for="(stu, index) in stus">
                <td>{{index + 1}}</td>
                <td>{{stu.stuNum}}</td>
                <td><img height="30" :src="stu.stuImg" /> </td>
                <td>{{stu.stuName}}</td>
                <td>
                    <table v-if="stu.stuGender == 'M'"></table>
                    <table v-if="stu.stuGender == 'F'"></table>
                </td>
                <td>{{stu.stuAge}}</td>
    
            </tr>
        </table>
    
    </div>
    
    <script type="text/javascript">
        var vm = new Vue({
            el: '#app-6',
            data: {
                message: 'Hello World!!',
                stus: [
                    {
                        stuNum: '10001',
                        stuName: '张三',
                        stuGender: 'M',
                        stuAge: 20,
                        stuImg: 'img/1.jpg'
                    },
                    {
                        stuNum: '10002',
                        stuName: '李四',
                        stuGender: 'M',
                        stuAge: 23,
                        stuImg: 'img/2.jpg'
                    },
                    {
                        stuNum: '10003',
                        stuName: '郑红',
                        stuGender: 'F',
                        stuAge: 19,
                        stuImg: 'img/3.jpg'
                    }
                ]
            }
        })
    
    </script>
    

    在这里插入图片描述

    3.6 表单标签的双向绑定 v-model

    • 只能使用在表单输入标签
    • v-model:value 可以简写为 v-model
    <div id="app-7">
        <input type="text" v-model="message">
        <hr /><br />
        双向绑定:{{message}}
    
    </div>
    
    <script type="text/javascript">
        var vm = new Vue({
            el: '#app-7',
            data: {
                message: 'Hello World!!'
            }
        })
    
    </script>
    

    四、vue 实例

    每个使用 vue 进行数据渲染的网页文档都需要创建一个 vue 实例 — — ViewModel

    4.1 vue 实例的生命周期

    vue 实例生命周期 — — vue 实例从创建到销毁的过程

    在这里插入图片描述

    • 创建 vue 实例 (初始化 data,加载 el)
    • 数据挂载 (将 vue 实例 data 中的数据渲染到网页 HTML 标签)
    • 重新渲染 (当 vue 的 data 数据发生变化,会重新渲染到 HTML 标签)
    • 销毁实例

    创建对象 ---- 属性初始化 ---- 获取属性值 ----- GC 回收

    4.2 钩子函数

    为了便于开发者在 vue 实例生命周期的不同阶段进行特定的操作,vue 在生命周期四个阶段的前后分别提供了一个函数,这个函数无需开发者调用,当 vue 实例到达生命周期的指定阶段会自动调用对应的函数。

    <div id="app-8">
        <label v-once>{{message}}</label><br />
        <label>{{message}}</label><br />
        <input type="text" v-model="message">
    
    </div>
    
    <script type="text/javascript">
        var vm = new Vue({
            el: '#app-8',
            data: {
                message: 'Hello World!!'
            },
            beforeCreate: function () {
                // 1. data 初始化之前执行,不能操作 data
            },
            create: function () {
                // 2. data 初始化之后执行,模板加载之前,可以修改 / 获取 data 中的值
                console.log(this.message);
                // this.message = 'Hello World!! create()';
            },
            beforeMount: function () {
                // 3. 模板加载之后,数据初始渲染(挂载)之前,可以修改 / 获取 data 中的值
                // this.message = 'Hello World!!  beforeMount';
            },
            mounted: function () {
                // 4. 数据初始渲染(挂载)之后,可以对 data 中的变量进行修改,但是不会影响 v-once 的渲染
                // this.message = "Hello World!!  mounted";
            },
            beforeUpdate: function () {
                // 5. 数据渲染之后,当 data 中的数据发生变化触发重新渲染,渲染之前执行此函数
                console.log("---" + this.message);
                this.message = 'Hello World!!  beforeUpdate';
            },
            update: function () {
                // 6. data 数据被修改之后,重新渲染到页面之后
                // this.message = "Hello World!!   update";
            },
            beforeDestroy: function () {
                // 7. 实例销毁之前
            },
            destroy: function () {
                // 8. 实例销毁之后
            }
        })
    
    </script>
    

    五、 计算属性和侦听器

    5.1 计算属性

    data 中的属性可以通过声明获得,也可以通过在 computed 计算属性的 getter 获得

    特性:计算属性所依赖的属性值发生变化会影响计算属性的值同时发生变化

    示例

    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>Title</title>
        <script src="js/vue.js"></script>
    </head>
    <body>
        <div id="app-9">
            <input type="text" v-model="message1"><br />
            <input type="text" v-model="message2"><br />
            {{message3}}
        </div>
    
    
        <script type="text/javascript">
            var vm = new Vue({
                el: '#app-9',
                data: {
                    message1: 'Hello',
                    message2: 'World'
                },
                computed: {
                    message3: function () {
                        return this.message1 + this.message2;
                    }
                }
            })
    
        </script>
    </body>
    </html>
    

    5.2 侦听器

    侦听器,就是 data 中属性的侦听器,当 data 中的属性值发生变化就会触发侦听器函数的执行

    虽然计算属性在大多数情况下更合适,但有时也需要一个自定义的侦听器。这就是为什么 Vue 通过 watch 选项提供了一个更通用的方法,来响应数据的变化。当需要在数据变化时执行异步或开销较大的操作时,这个方式是最有用的。

    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>Title</title>
        <script src="js/vue.js"></script>
    </head>
    <body>
        <div id="app-10">
            <input type="text" v-model="message1"><br />
            <input type="text" v-model="message2"><br />
            {{message3}}
        </div>
    
    
        <script type="text/javascript">
            var vm = new Vue({
                el: '#app-10',
                data: {
                    message1: 'Hello',
                    message2: 'World',
                    message3: 'Hello World'
                },
                watch: {
                    message1: function () {
                        this.message3 = this.message1 + this.message2;
                    },
                    message2: function () {
                        this.message3 = this.message1 + this.message2;
                    }
                }
            })
    
        </script>
    </body>
    </html>
    

    六、class 与 style 绑定

    6.1 class 绑定

    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>Title</title>
        <style>
            .my-style1 {
                width: 200px;
                height: 100px;
                background: orange;
            }
            .my-style2 {
                border-radius: 10px;
            }
            .my-style3 {
                width: 200px;
                height: 100px;
                background: black;
            }
        </style>
        <script src="js/vue.js"></script>
    </head>
    <body>
        <div id="app-11">
            <!-- 如果 message1 为 true, 就加载 my-style1,如果 message2 为 true, 就加载 my-style2  -->
            <div :class="{'my-style1': message1, 'my-style2' : message2}">
            </div><hr />
            <!-- 为 class 属性加载多个样式名 -->
            <div :class="[booleanValue1, booleanValue2]">
            </div><hr />
            <!-- 如果 message3 为 true, 则 class = 'my-style3',否则 class = 'my-style1'
            如果在三目运算中使用样式名则需要加单引号,不加单引号则表示从 data 变量中获取样式名
            -->
            <div :class="[message3 ? 'my-style3' : 'my-style1']">
            </div>
            <div :class="[message1 ? booleanValue1 : booleanValue3]"></div>
        </div>
    
    
        <script type="text/javascript">
            var vm = new Vue({
                el: '#app-11',
                data: {
                    message1: true,
                    message2: true,
                    message3: true,
                    booleanValue1: "my-style1",
                    booleanValue2: "my-style2",
                    booleanValue3: "my-style3"
                }
            })
    
        </script>
    </body>
    </html>
    

    在这里插入图片描述

    6.2 style 绑定

    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>Title</title>
        <script src="js/vue.js"></script>
    </head>
    <body>
        <div id="app-12">
            <!-- 当使用 v-bind 绑定内联样式时:
                1. 使用 {} 定义 style 样式,才能获取 data 的值, {} 要遵循 JSON 格式
                2. {} 中不在使用 style 样式属性名 “font-size”, 而要使用对应的 js 属性名
                border-style-width --- borderStyleWidth
             -->
            <div v-bind:style="{color: colorName, fontSize: fontsize + 'px' }">
                Hello World!
            </div>
            <!-- 我们可以直接为 style 属性绑定一个 data 中定义好的内联样式的字符串 -->
            <div v-bind:style="myStyle1">
                Hello World!!
            </div>
            <!-- 我们可以直接为 style 属性绑定一个 data 中定义好的内联样式的对象 -->
            <div v-bind:style="myStyle2">
                Hello World!!!
            </div>
            <!-- 我们可以在同一个 style 属性通过数组引用多个内联样式的对象 -->
            <div v-bind:style="[myStyle2, myStyle3]">
                Hello World!!!!
            </div>
        </div>
    
    
        <script type="text/javascript">
            var vm = new Vue({
                el: '#app-12',
                data: {
                    colorName: "yellow",
                    fontsize: "40",
                    myStyle1: "color: orange; font-size: 50px",
                    myStyle2: {
                        color: "blue",
                        fontSize: "60px"
                    },
                    myStyle3: {
                        textShadow: "orange 3px 3px 5px"
                    }
                }
            })
    
        </script>
    </body>
    </html>
    

    在这里插入图片描述

    七、条件与列表渲染

    7.1 条件渲染

    条件判断语句:

    • v-if
    • v-else-if
    • v-else

    7.1.1 v-if

    v-if 指令用于条件性地渲染一块内容。这块内容只会在指令的表达式返回 truthy 值的时候被渲染。

    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>Title</title>
        <script src="js/vue.js"></script>
    </head>
    <body>
        <div id="app-13">
            <h3 v-if="code == 1">Hello :可以看到</h3>
            <h3 v-if="flag">flag 为 true, 可以看到</h3>
        </div>
    
    
        <script type="text/javascript">
            var vm = new Vue({
                el: '#app-13',
                data: {
                    code: 1,
                    flag: false
                }
            })
    
        </script>
    </body>
    </html>
    

    在这里插入图片描述

    7.1.2 v-else

    v-else 指令来表示 v-if 的“else 块”

        <div id="app-13">
            <!-- v-else 标签需要紧跟在 v-if 的标签之后,中间不能有其他标签, 否则它将不会被识别 -->
            <h3 v-if="code == 1">Hello :可以看到</h3>
            <h3 v-else>World :可以看到</h3>
        </div>
    
    
        <script type="text/javascript">
            var vm = new Vue({
                el: '#app-13',
                data: {
                    code: 1
                }
            })
    
        </script>
    

    7.1.3 v-else-if

        <div id="app-13">
            分数 {{code}}
            对应的等级:
            <h3 v-if="code >= 90">优秀</h3>
            <h3 v-else-if="code >= 80">良好</h3>
            <h3 v-else-if="code >= 70">中等</h3>
            <h3 v-else-if="code >= 60">及格</h3>
            <h3 v-else>挂科</h3>
        </div>
    
    
        <script type="text/javascript">
            var vm = new Vue({
                el: '#app-13',
                data: {
                    code: 85
                }
            })
        </script>
    

    在这里插入图片描述

    7.1.4 v-show

    v-show :同样用于根据条件展示元素。

    从功能上 v-show 与 v-if 作用是相同的,只是渲染过程有区别。

    v-if 与 v-show 的区别:

    • v-if 是“真正”的条件渲染,因为它会确保在切换过程中条件块内的事件监听器和子组件适当地被销毁和重建。
    • v-if 也是惰性的:如果在初始渲染时条件为假,则什么也不做——直到条件第一次变为真时,才会开始渲染条件块。
    • 相比之下,v-show 就简单得多——不管初始条件是什么,元素总是会被渲染,并且只是简单地基于 CSS 进行切换。
    • 一般来说,v-if 有更高的切换开销,而 v-show 有更高的初始渲染开销。因此,如果需要非常频繁地切换,则使用 v-show 较好;如果在运行时条件很少改变,则使用 v-if 较好。

    7.2 列表渲染

    编码过程中,发现网页出现报错:

    Uncaught Error: Bootstrap's JavaScript requires jQuery at bootstrap.min.js:6

    解决方法:在引进JQuery文件时,将其放在 bootstrap 前面即可。

    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>Title</title>
        <script src="https://cdn.staticfile.org/jquery/1.10.2/jquery.min.js"></script>
        <!-- 最新版本的 Bootstrap 核心 CSS 文件 -->
        <link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/3.4.1/css/bootstrap.min.css" integrity="sha384-HSMxcRTRxnN+Bdg0JdbxYKrThecOKuH5zCYotlSAcp1+c8xmyTe9GYg1l9a69psu" crossorigin="anonymous">
        <!-- 最新的 Bootstrap 核心 JavaScript 文件 -->
        <script src="https://stackpath.bootstrapcdn.com/bootstrap/3.4.1/js/bootstrap.min.js" integrity="sha384-aJ21OjlMXNL5UyIl/XNwTMqvzeRMZH2w8c5cRVpzpU8Y5bApTppSuUkhZXN0VxHd" crossorigin="anonymous"></script>
    
        <script src="js/vue.js"></script>
    </head>
    <body>
        <div id="app-14">
           <ul>
               <li v-for="c in categories">
                   <a :href="'query?cid=' + c.cid">{{c.cname}}</a>
               </li>
           </ul>
    
            <table class="table table-bordered">
                <tr>
                    <th>学号</th>
                    <th>照片</th>
                    <th>姓名</th>
                    <th>性别</th>
                    <th>年龄</th>
                    <th>操作</th>
                </tr>
                <template v-for="(s, index) in stu">
                    <tr :id="'tr' + s.stuNum">
                        <td>{{s.stuNum}}</td>
                        <td>
                            <img height="30" :src="s.stuImg" />
                        </td>
                        <td>{{s.stuName}}</td>
                        <td>
                            <!-- {{s.stuGender == 'M' ? '男' : '女'}} -->
                            <img v-if="s.stuGender == 'M'" src="img/m.bmp">
                            <img v-else src="img/f.bmp">
                        </td>
                        <td>{{s.stuAge}}</td>
                        <td>
                            <a class="btn btn-danger" :href="'stu/delete?cid=' + s.stuNum">删除</a>
                            <a class="btn btn-success" :href="'stu/update?cid=' + s.stuNum">修改</a>
                        </td>
                    </tr>
                </template>
    
            </table>
        </div>
    
        <script type="text/javascript">
            var vm = new Vue({
                el: '#app-14',
                data: {
                    categories:[
                        {
                            cid: 1,
                            cname: "华为"
                        },
                        {
                            cid: 2,
                            cname: "小米"
                        },
                        {
                            cid: 3,
                            cname: "OPPO"
                        },
                        {
                            cid: 4,
                            cname: "VIVO"
                        }
                    ],
                    stu: [
                        {
                            stuNum: "10010",
                            stuImg: "img/1.jpg",
                            stuName: "Tom",
                            stuGender: "M",
                            stuAge: 20
                        },
                        {
                            stuNum: "10011",
                            stuImg: "img/2.jpg",
                            stuName: "Joker",
                            stuGender: "M",
                            stuAge: 21
                        },
                        {
                            stuNum: "10012",
                            stuImg: "img/3.jpg",
                            stuName: "Ling",
                            stuGender: "F",
                            stuAge: 20
                        },
                        {
                            stuNum: "10013",
                            stuImg: "img/1.jpg",
                            stuName: "Jack",
                            stuGender: "F",
                            stuAge: 18
                        },
                    ]
                }
            })
        </script>
    </body>
    </html>
    

    八、事件处理

    • 在使用 vue 进行数据渲染时,如果使用原生 js 事件绑定 (例如 onclick),如果需要获取 vue 实例中的数据并传参则需要通过拼接来完成

    • vue 提供了 v-on 指令用于绑定各种事件 (v-on:click),简化了从 vue 取值的过程,但是触发的方法需要定义在 vue 实例的 methods 中

      <button class="btn btn-danger" v-on:click="doDelete(s.stuNum,s.stuName)">删除</button>
      
      <script type="text/javascript">
          var vm = new Vue({
              el: '#app-15',
              data: {
                  stu: [
                      {
                          stuNum: "10010",
                          stuImg: "img/1.jpg",
                          stuName: "Tom",
                          stuGender: "M",
                          stuAge: 20
                      }
                  ]
              },
              methods: {
                  doDelete: function (sNum, sName) {
                      alert("---delete:" + sNum + " " + sName)
                  }
              }
          })
      </script>
      
    • v-on:click 可以简写为 @click

    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>Title</title>
        <script src="https://cdn.staticfile.org/jquery/1.10.2/jquery.min.js"></script>
        <!-- 最新版本的 Bootstrap 核心 CSS 文件 -->
        <link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/3.4.1/css/bootstrap.min.css" integrity="sha384-HSMxcRTRxnN+Bdg0JdbxYKrThecOKuH5zCYotlSAcp1+c8xmyTe9GYg1l9a69psu" crossorigin="anonymous">
        <!-- 最新的 Bootstrap 核心 JavaScript 文件 -->
        <script src="https://stackpath.bootstrapcdn.com/bootstrap/3.4.1/js/bootstrap.min.js" integrity="sha384-aJ21OjlMXNL5UyIl/XNwTMqvzeRMZH2w8c5cRVpzpU8Y5bApTppSuUkhZXN0VxHd" crossorigin="anonymous"></script>
    
        <script src="js/vue.js"></script>
    </head>
    <body>
        <div id="app-15">
           <ul>
               <li v-for="c in categories">
                   <a :href="'query?cid=' + c.cid">{{c.cname}}</a>
               </li>
           </ul>
    
            <table class="table table-bordered">
                <tr>
                    <th>学号</th>
                    <th>照片</th>
                    <th>姓名</th>
                    <th>性别</th>
                    <th>年龄</th>
                    <th>操作</th>
                </tr>
                <template v-for="(s, index) in stu">
                    <tr :id="'tr' + s.stuNum">
                        <td>{{s.stuNum}}</td>
                        <td>
                            <img height="30" :src="s.stuImg" />
                        </td>
                        <td>{{s.stuName}}</td>
                        <td>
                            <!-- {{s.stuGender == 'M' ? '男' : '女'}} -->
                            <img v-if="s.stuGender == 'M'" src="img/m.bmp">
                            <img v-else src="img/f.bmp">
                        </td>
                        <td>{{s.stuAge}}</td>
                        <td>
                            <button class="btn btn-danger" v-on:click="doDelete(s.stuNum,s.stuName)">删除</button>
                            <button class="btn btn-success" @click="doUpdate" :data-snum="s.stuNum"
                                    :data-sname="s.stuName" :data-simg="s.stuImg">修改</button>
                        </td>
                    </tr>
                </template>
    
            </table>
        </div>
    
        <script type="text/javascript">
            var vm = new Vue({
                el: '#app-15',
                data: {
                    categories:[
                        {
                            cid: 1,
                            cname: "华为"
                        },
                        {
                            cid: 2,
                            cname: "小米"
                        },
                        {
                            cid: 3,
                            cname: "OPPO"
                        },
                        {
                            cid: 4,
                            cname: "VIVO"
                        }
                    ],
                    stu: [
                        {
                            stuNum: "10010",
                            stuImg: "img/1.jpg",
                            stuName: "Tom",
                            stuGender: "M",
                            stuAge: 20
                        },
                        {
                            stuNum: "10011",
                            stuImg: "img/2.jpg",
                            stuName: "Joker",
                            stuGender: "M",
                            stuAge: 21
                        },
                        {
                            stuNum: "10012",
                            stuImg: "img/3.jpg",
                            stuName: "Ling",
                            stuGender: "F",
                            stuAge: 20
                        },
                        {
                            stuNum: "10013",
                            stuImg: "img/1.jpg",
                            stuName: "Jack",
                            stuGender: "F",
                            stuAge: 18
                        },
                    ]
                },
                methods: {
                    doDelete: function (sNum, sName) {
                        alert("---delete:" + sNum + " " + sName)
                    },
                    doUpdate: function (event) {
                        // 如果 v-on 绑定的 js 函数没有参数,调用的时候可以省略 (), 同时可以给 js 函数一个 event 参数(事件对象)
                        // 1. event 表示触发当前函数的事件
                        // 2. event.srcElement 表示发生事件的元素 --- 修改按钮
                        // 3. event.srcElement.dataset 表示按钮上绑定的数据集 (data-开头的属性)
                        alert("---update:");
                        let stu = event.srcElement.dataset;
                    }
                }
            })
        </script>
    </body>
    </html>
    

    8.1 使用 JS 函数传值

    <button class="btn btn-danger" v-on:click="doDelete(s.stuNum,s.stuName)">删除</button>
    
    <script type="text/javascript">
        var vm = new Vue({
            el: '#app-15',
            data: {
                stu: [
                    {
                        stuNum: "10010",
                        stuImg: "img/1.jpg",
                        stuName: "Tom",
                        stuGender: "M",
                        stuAge: 20
                    }
                ]
            },
            methods: {
                doDelete: function (sNum, sName) {
                    alert("---delete:" + sNum + " " + sName)
                }
            }
        })
    </script>
    

    8.2 使用 dataset 对象传值 (推荐)

    <button class="btn btn-success" @click="doUpdate" :data-snum="s.stuNum"
                                    :data-sname="s.stuName" :data-simg="s.stuImg">修改</button>
    
    <script type="text/javascript">
        var vm = new Vue({
            el: '#app-15',
            data: {
                stu: [
                    {
                        stuNum: "10010",
                        stuImg: "img/1.jpg",
                        stuName: "Tom",
                        stuGender: "M",
                        stuAge: 20
                    }
                ]
            },
            methods: {
                doUpdate: function (event) {
                        // 如果 v-on 绑定的 js 函数没有参数,调用的时候可以省略 (), 同时可以给 js 函数一个 event 参数(事件对象)
                        // 1. event 表示触发当前函数的事件
                        // 2. event.srcElement 表示发生事件的元素 --- 修改按钮
                        // 3. event.srcElement.dataset 表示按钮上绑定的数据集 (data-开头的属性)
                        alert("---update:");
                        let stu = event.srcElement.dataset;
                    }
            }
        })
    </script>
    

    8.3 混合使用

    有时也需要在内联语句处理器中访问原始的 DOM 事件。可以用特殊变量 $event 把它传入方法

    <button class="btn btn-danger" v-on:click="doDelete(s.stuNum,s.stuName, $event)" :data-simg="s.stuImg">删除</button>
    
    <script type="text/javascript">
        var vm = new Vue({
            el: '#app-15',
            data: {
                stu: [
                    {
                        stuNum: "10010",
                        stuImg: "img/1.jpg",
                        stuName: "Tom",
                        stuGender: "M",
                        stuAge: 20
                    }
                ]
            },
            methods: {
                doDelete: function (sNum, sName, event) {
                    alert("---delete:" + sNum + " " + sName)
                    console.log(event.srcElement.dataset)
                }
            }
        })
    </script>
    

    8.4 事件修饰符

    修饰符是由点开头的指令后缀来表示的。

    当使用 v-on 进行事件绑定的时候,可以添加特定后缀,设置事件触发的特性

    8.4.1 事件修饰符使用示例

    <button type="submit" class="btn btn-success" @click.prevent="test">修改</button>
    

    8.4.2 事件修饰符

    常用的事件修饰符:

    • .stop
    • .prevent
    • .capture
    • .self
    • .once
    • .passive

    .prevent 用来阻止标签的默认行为

    <div id="app-16">
        <form action="https://www.baidu.com">
             <!-- 此处不加 .prevent ,网页会跳转到 https://www.baidu.com -->
            <button type="submit" class="btn btn-success" @click.prevent="test">修改</button>
        </form>
    </div>
    
    <script type="text/javascript">
        var vm = new Vue({
            el: '#app-16',
            data: {},
            methods: {
    
                test: function (event) {
                    alert("--test");
                }
            }
        })
    </script>
    

    .stop 阻止事件冒泡

    .self 设置只能自己触发事件(子标签不能触发)

    <div id="app-16">
        <!-- .prevent 示例 -->
        <form action="https://www.baidu.com">
            <!-- 此处不加 .prevent ,网页会跳转到 https://www.baidu.com -->
            <button type="submit" class="btn btn-success" @click层="test">修改</button>
        </form>
        <!-- .stop 示例 .self 示例:只能点击自己触发 -->
        <div style="width: 200px; height: 200px; background: red;" @click.self="outside">
            <div style="width: 100px; height: 100px; background: yellow;" @click="inside">
                <!-- 此处加了 .stop , 网页的外层 div  父标签不会触发 -->
                <button @click.stop="itself">test stop 修饰符</button>
            </div>
        </div>
    
    </div>
    
    <script type="text/javascript">
        var vm = new Vue({
            el: '#app-16',
            data: {},
            methods: {
                test: function (event) {
                    alert("--test");
                },
                inside: function () {
                    alert("--inside");
                },
                outside: function () {
                    alert("--outside");
                },
                itself: function () {
                    alert("--itself");
                }
            }
        })
    </script>
    

    .once 限定事件只能触发一次

    <!-- .once 示例:test()方法只执行一次, -->
    <form action="https://www.baidu.com">
        <!-- 加了 .prevent,第一次点击执行 test(),默认跳转被阻止, 第二次点击按钮,直接跳转, test()不执行 -->
        <button type="submit" class="btn btn-success" @click.prevent.once="test">修改</button>
    </form>
    

    8.5 按键修饰符

    按键修饰符:针对键盘事件的修饰符,限定哪个按键会触发事件

    常用的按键修饰符:

    • .enter
    • .tab
    • .delete (捕获“删除”和“退格”键)
    • .esc
    • .space
    • .up
    • .down
    • .left
    • .right

    .enter 只有在 keyEnter 时调用(触发 enter 按键之后触发事件)

    <div id="app-17">
         <input type="text" @keyup.enter="test">
    </div>
    
    <script type="text/javascript">
        var vm = new Vue({
            el: '#app-17',
            data: {},
            methods: {
                test: function () {
                    alert("enter松开触发")
                }
            }
        })
    </script>
    

    还可以通过全局 config.keyCodes 对象自定义按键修饰符别名

    // 输入 按键 j 触发事件 test
    <input type="text" @keyup.aaa="test">
    // 按键 j 的别名
    Vue.config.keyCodes.aaa = 74
    

    8.6 系统修饰符

    组合键

    示例:CTRL + J 触发事件

    <div id="app-17">
        <input type="text" @keyup.ctrl.j="test">
    </div>
    
    <script type="text/javascript">
        Vue.config.keyCodes.j = 74
        var vm = new Vue({
            el: '#app-17',
            data: {},
            methods: {
                test: function () {
                    alert("enter松开触发")
                }
            }
        })
    </script>
    

    常用的修饰符:

    • .ctrl
    • .alt
    • .shift
    • .metawindows 键

    九、表单输入绑定

    表单输入绑定,即双向绑定:就是能够将 vue 实例的 data 数据渲染到表单输入视图 (input\textarea\select),

    也能够将输入视图的数据同步到 vue 实例的 data中。

    <div id="app-18">
        <!-- 文本输入框 密码输入框 -->
        <input type="text" v-model="name" /><br />
        <input type="password" v-model="password" />
        <hr />
        <!-- 单选按钮 -->
        <input type="radio" v-model="radioTest" value="A" /> A
        <input type="radio" v-model="radioTest" value="B" /> B
        <input type="radio" v-model="radioTest" value="C" /> C
        <input type="radio" v-model="radioTest" value="D" /> D
        <hr />
    
        <!-- 复选框,绑定的是一个数组 -->
        <input type="checkbox" v-model="checkBox" value="篮球" /> 篮球 <br />
        <input type="checkbox" v-model="checkBox" value="足球" /> 足球 <br />
        <input type="checkbox" v-model="checkBox" value="羽毛球" /> 羽毛球 <br />
        <input type="checkbox" v-model="checkBox" value="乒乓球" /> 乒乓球 <br />
    
        <!-- 下拉菜单 select:绑定一个字符串 -->
        <select v-model="city">
            <option value="BJ">北京</option>
            <option value="SH">上海</option>
            <option value="SZ">深圳</option>
            <option value="GZ">广州</option>
        </select>
        <hr />
    
        <!-- 下拉菜单 select:加上了 multiple ,表示可多选,需要绑定一个数组 -->
        <select v-model="cities" multiple>
            <option value="BJ">北京</option>
            <option value="SH">上海</option>
            <option value="SZ">深圳</option>
            <option value="GZ">广州</option>
        </select>
    
        <button type="button" @click="test">测试</button>
    </div>
    
    <script type="text/javascript">
    
        var vm = new Vue({
            el: '#app-18',
            data: {
                name: "admin",
                password: "123456",
                radioTest: "C",
                checkBox: [],
                city: "",
                cities: []
            },
            methods: {
                test: function () {
                    alert(vm.cities)
                }
            }
    
        })
    </script>
    

    十、组件

    10.1 组件介绍及示例

    组件,就是讲通用的 HTML 模块进行封装 —— 可复用的 Vue 实例

    ​ 通常一个应用会以一棵嵌套的组件树的形式来组织:

    在这里插入图片描述

    10.1.1 组件注册

    将通用的 HTML 模块封装注册到 vue 中

    自定义组件 my-components.js:

    Vue.component('header-button', {
        template: `<div style="width: 100%; height: 80px; background: salmon">
                    <table width="100%">
                        <tr>
                            <td width="200" align="right" valign="middle">
                                <img src="img/1.jpg" height="80" />
                            </td>
                            <td>
                                <label style="color: deepskyblue; font-size: 32px; font-family: 'Adobe 楷体 Std R'; margin-left: 30px">
                                    登录
                                </label>
                            </td>
                        </tr>
                    </table>
                </div>`
    });
    

    10.1.2 组件引用

    • 定义组件需要依赖 vue.js,在引用自定义组件 js 文件要先引用 vue.js
    • 组件的引用必须在 vue 实例 el 指定的容器中 ,即要在Vue实例范围内
    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>Title</title>
        <script src="https://cdn.staticfile.org/jquery/1.10.2/jquery.min.js"></script>
        <!-- 最新版本的 Bootstrap 核心 CSS 文件 -->
        <link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/3.4.1/css/bootstrap.min.css" integrity="sha384-HSMxcRTRxnN+Bdg0JdbxYKrThecOKuH5zCYotlSAcp1+c8xmyTe9GYg1l9a69psu" crossorigin="anonymous">
        <!-- 最新的 Bootstrap 核心 JavaScript 文件 -->
        <script src="https://stackpath.bootstrapcdn.com/bootstrap/3.4.1/js/bootstrap.min.js" integrity="sha384-aJ21OjlMXNL5UyIl/XNwTMqvzeRMZH2w8c5cRVpzpU8Y5bApTppSuUkhZXN0VxHd" crossorigin="anonymous"></script>
    
        <script src="js/vue.js"></script>
    </head>
    <body>
        <div id="app-19">
            <header-button></header-button>
            <hr />
            <header-button></header-button>
        </div>
        <script src="js/my-components.js"></script>
        <script type="text/javascript">
    
            var vm = new Vue({
                el: '#app-19'
            })
        </script>
    </body>
    </html>
    

    在这里插入图片描述

    10.2 组件注册

    10.2.1 自定义组件的结构

    • Vue.component() 注册组件
    • data 定义组件的模板渲染的数据
    • template 组件的 HTML 模块(HTML 标签 \ CSS 样式)
    • methods 定义组件中的标签事件中绑定的 JS 函数

    my-components.js:

    Vue.component('header-button', {
        data: function () {
            // 组件中 data 是通过函数返回的对象
            return {
                name: "貂蝉"
            };
        },
        template: `<div style="width: 100%; height: 80px; background: salmon">
                    <table width="100%">
                        <tr>
                            <td width="200" align="right" valign="middle">
                                <img src="img/1.jpg" height="80" />
                            </td>
                            <td>
                                <label style="color: deepskyblue; font-size: 32px; font-family: 'Adobe 楷体 Std R'; margin-left: 30px">
                                    登录人: {{name}}
                                </label>
                            </td>
                            <td>
                                <button @click="test">组件按钮</button>
                            </td>
                        </tr>
                    </table>
                </div>`,
        methods: {
            test: function () {
                alert("组件中 header-button 定义的函数事件")
            }
        }
    });
    

    10.2.2 组件的封装

    • 将模板中的 css 样式提取出来,单独封装到 css 文件存储在 css 目录
    • 将模板中的图片存储在 img 目录
    • 将定义组件的 js 文件和 vue 文件存放到 js 目录
    Vue 组件封装的结构
    在这里插入图片描述

    :在编码过程中学到,Vue 中同一个 DOM 元素绑定多个点击事件:可以使用逗号分隔。

    10.2.3 组件的复用

    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>Title</title>
        <link rel="stylesheet" href="css/my-components.css" />
        <script src="https://cdn.staticfile.org/jquery/1.10.2/jquery.min.js"></script>
        <!-- 最新版本的 Bootstrap 核心 CSS 文件 -->
        <link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/3.4.1/css/bootstrap.min.css" integrity="sha384-HSMxcRTRxnN+Bdg0JdbxYKrThecOKuH5zCYotlSAcp1+c8xmyTe9GYg1l9a69psu" crossorigin="anonymous">
        <!-- 最新的 Bootstrap 核心 JavaScript 文件 -->
        <script src="https://stackpath.bootstrapcdn.com/bootstrap/3.4.1/js/bootstrap.min.js" integrity="sha384-aJ21OjlMXNL5UyIl/XNwTMqvzeRMZH2w8c5cRVpzpU8Y5bApTppSuUkhZXN0VxHd" crossorigin="anonymous"></script>
    
        <script src="js/vue.js"></script>
    </head>
    <body>
        <div id="app-19">
            <header-button></header-button>
            <hr />
            <header-button></header-button>
        </div>
        <script src="js/my-components.js"></script>
        <script type="text/javascript">
    
            var vm = new Vue({
                el: '#app-19'
            })
        </script>
    </body>
    </html>
    

    10.3 组件通信

    vue 实例本身就是一个组件(模板就是 el 指定容器,data 就是组件数据,methods 就是组件的事件函数)

    在 vue 实例指定的 el 容器中引用的组件称为子组件,当前 vue 实例就是父组件

    注:子组件按钮模板不能触发父组件的方法,子组件的按钮可以触发子组件的方法。

    10.3.1 父传子

    vue 实例引用组件的时候,传递数据到引用的组件中

    通过组件的属性实现父组件传递数据到子组件

    示意图
    在这里插入图片描述

    10.3.2 子传父 – 使用 props 属性动态传递参数

    通过子组件的按钮“调用”父组件的函数,通过函数传值

    流程示意图
    在这里插入图片描述

    父组件:

    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>Title</title>
        <link rel="stylesheet" href="css/my-components.css" />
        <script src="js/vue.js"></script>
    </head>
    <body>
        <div id="app-21">
            <!-- 组件的引用必须在 vue 实例指定的容器中 -->
            <header-bar :name="message" @my-event="parentMethod"></header-bar>
            子组件传到父组件的标题名称: {{title}}
            <hr />
            <header-bar name="关羽"></header-bar>
        </div>
        <script src="js/my-components-bar2.js"></script>
        <script type="text/javascript">
    
            var vm = new Vue({
                el: '#app-21',
                data: {
                    message: "貂蝉",
                    title: ""
                },
                methods: {
                    parentMethod: function (res) {
                        vm.title = res;
                    }
                }
            })
        </script>
    </body>
    </html>
    

    子组件:

    Vue.component('header-bar', {
        data: function() {
            return {
                title: "三国 -- √"
            }
        },
        template: `<div class="divStyle">
                    <table class="tableStyle">
                        <tr>
                            <td width="200" align="right" valign="middle">
                                <img src="img/1.jpg" class="logoImg" />
                            </td>
                            <td>
                                <label class="nameStyle">
                                    登录人: {{name}}
                                </label>
                            </td>
                            <td>
                                <button @click="childMethod">组件按钮点击次数</button>
                            </td>
                        </tr>
                    </table>
                </div>`,
        props: ["name"],
        methods: {
            childMethod: function () {
                this.$emit("my-event", this.title);
            }
        }
    });
    

    在这里插入图片描述

    10.3.3 总结

    父组件通信子组件

    • props: 子组件通过props获取定义父组件传递的自定义属性

    • this.$refs: 引用子组件

    • this.$children: 父组件childrens属性,存储着所有的子组件

    子组件通信父组件(或根组件)

    • this.$emit: 子组件通过$emit访问父组件传递的自定义事件

    • this.$parent: 访问父组件

    • this.$root: 访问根组件。根组件root就是new Vue({el: "#app"}); 中的el元素

    10.4 组件插槽

    当我们自定义 vue 组件时,允许组件中的部分内容在调用组件时进行定义 —— 插槽

    10.4.1 插槽的使用

    • 在自定义组件时通过 slot 标签在组件的模板中定义插槽

    my-components-bar-slot.js:

    Vue.component('header-bar', {
        data: function() {
            return {
                title: "三国 -- √"
            }
        },
        template: `<div class="divStyle">
                    <table class="tableStyle">
                        <tr>
                            <td width="200" align="right" valign="middle">
                                <img src="img/1.jpg" class="logoImg" />
                            </td>
                            <td>
                                <label class="nameStyle">
                                    登录人: {{name}}
                                </label>
                            </td>
                            <td>
                                <slot></slot>
                            </td>
                            <td>
                                <button @click="childMethod">组件按钮点击次数</button>
                            </td>
                        </tr>
                    </table>
                </div>`,
        props: ["name"],
        methods: {
            childMethod: function () {
                this.$emit("my-event", this.title);
            }
        }
    });
    
    • 在父组件中调用此组件时,指定插槽填充的模板

    示例1:插槽填充 搜索框

    <header-bar :name="message">
         <input /> <button>搜索</button>
    </header-bar>
    

    在这里插入图片描述

    示例2:插槽填充 按钮

    <header-bar :name="message" @my-event="parentMethod">
         <div>
             <a href="#">首页</a>
             <a href="#">后台</a>
             <a href="#">管理</a>
             <a href="#">关于</a>
         </div>
    </header-bar>
    

    在这里插入图片描述

    10.4.2 具名插槽

    当组件中的插槽数量 > 1 时,需要给组件中的 slot 标签添加 name 属性指定插槽的名字

    • 定义组件
    Vue.component('page-frame', {
        template:  `<div>
                <div id="header" style="width: 100%; height: 100px; background: pink">
                    {{title}}<br />
                    slot1 : <br />
                    <slot name="slot1"></slot>
                </div>
                <div style="width: 100%; height: 580px">
                    slot2 : <br />
                    <slot name="slot2"></slot>
                </div>
                <div id="footer" style="width: 100%; height: 40px; background: lightblue">{{cr}}</div>
            </div>`,
        props: ["title", "cr"]
    });
    
    • 引用组件
    <div id="app-22">
         <!-- 组件的引用必须在 vue 实例指定的容器中 -->
         <page-frame title="标题" cr="地址">
             <template slot="slot1">
                 <input /> <button>搜索</button>
             </template>
             <template slot="slot2">
                 <div>
                     <a href="#">首页</a>
                     <a href="#">后台</a>
                     <a href="#">管理</a>
                     <a href="#">关于</a>
                 </div>
             </template>
         </page-frame>
    </div>
    

    10.4.3 插槽作用域

    • 定义组件时,将组件中的数据绑定到 slot 标签

    my-components-bar-slot.js:

    Vue.component('page-frame-scope', {
        template:  `<div>
                <div id="header" style="width: 100%; height: 100px; background: pink">
                    {{title}}<br />
                    slot1 : <br />
                    <slot name="slot1"></slot>
                </div>
                <div style="width: 100%; height: 580px">
                    slot2 : <br />
                    <slot name="slot2" v-bind:sites="sites"></slot>
                </div>
                <div id="footer" style="width: 100%; height: 40px; background: lightblue">{{cr}}</div>
            </div>`,
        props: ["title", "cr"],
        data: function () {
            return {
                sites: [
                    {
                        "name": "菜鸟教程",
                        "url": "www.runoob.com"
                    },
                    {
                        "name": "google",
                        "url": "www.google.com"
                    },
                    {
                        "name": "微博",
                        "url": "www.weibo.com"
                    }
                ]
            }
        }
    });
    
    • 引用组件时,在填充插槽的模板上使用 slot-scopt 属性获取插槽绑定的值
    <page-frame-scope title="标题" cr="地址">
        <template slot="slot1">
            <input /> <button>搜索</button>
        </template>
        <template slot="slot2" slot-scope="res">
            <table class="table table-bordered">
                <tr>
                    <th>名称</th>
                    <th>网站</th>
                </tr>
                <tr v-for="site in res.sites">
                    <td>{{site.name}}</td>
                    <td>{{site.url}}</td>
                </tr>
            </table>
        </template>
    </page-frame-scope>
    

    十一、axios 异步通信

    11.1 axios 介绍

    vue 可以实现数据的渲染,但是如何获取数据呢?

    vue 本身不具备通信能力,通常结合 axios —— 一个专注于异步通信的 js 框架来使用(Vue.js 2.0 版本推荐使用 axios 来完成 ajax 请求。)

    • axios 数据通信
    • vue 数据渲染
    • 什么是 axios ?

    ​ Axios 是一个基于 promise 的 HTTP 库,可以用在浏览器和 node.js 中。

    • 菜鸟教程 axios 说明文档:https://www.runoob.com/vue2/vuejs-ajax-axios.html
    • 中文文档:http://www.axios-js.com/

    11.2 axios 入门使用

    • axios —— 实现步骤复杂
    • JQuery 笨重
    • axios 简洁、高效,对 RESTful 支持良好

    11.3 axios 异步请求方法

    axios 提供了多种异步请求方法,实现对 RESTful 风格的支持

    11.3.1 GET 格式的请求

    • axios.get(url).then(function);

      • 使用 response.data 读取 JSON 数据:

        axios
            .get('json/json_demo.json')
            .then(response => (this.info = response.data.sites))
            .catch(function (error) {
            console.log(error)
        })
        
    • axios.get(url,{}).then(function);

      • GET 方法传递参数格式 (使用 axios 的 get 请求传递参数,需要将参数设置在 params 下)

        // 直接在 URL 上添加参数 ID=12345
        axios.get('/user?ID=12345')
          .then(function (response) {
            console.log(response);
          })
          .catch(function (error) {
            console.log(error);
          });
         
        // 也可以通过 params 设置参数:
        axios.get('/user', {
            params: {
              ID: 12345
            }
          })
          .then(function (response) {
            console.log(response);
          })
          .catch(function (error) {
            console.log(error);
          });
        

    11.3.2 POST 格式的请求

    • axios.post(url, {}).then(function);

      • axios
            .post("https://localhost:9098/blog/upload", {
            name: "张三",
            age: "20"
        
        })
            .then(response => (this.info2 = response))
            .catch(function (error) {
            console.log(error)
        })
        

    11.3.3 自定义请求

    自定义请求:自定义请求方式、请求参数、请求头、请求体(post)

    axios({
        url: "https://localhost:9098/blog/upload",
        method: "post",
        params: {
            // 设置请求行传值
            name: "张三",
            limit: 15
        },
        headers: {
            // 设置请求头
        },
        data: {
            // 设置请求体 (post / put)
        }
    }).then(function (res) {
        console.log(res)
    });
    

    11.3.4 请求方法别名

    • axios.request(config)
    • axios.get(url[, config])
    • axios.delete(url[, config])
    • axios.head(url[, config])
    • axios.post(url[, data[, config]])
    • axios.put(url[, data[, config]])
    • axios.patch(url[, data[, config]])

    当使用别名方法时,不需要在config中指定url,method和data属性。

    11.4 并发请求

    axios.all()、axios.spread() 两个辅助函数用于处理同时发送多个请求,可以实现在多个请求都完成后再执行一些逻辑。

    处理并发请求的助手函数:

    • axios.all(iterable)
    • axios.spread(callback)
    <div id="app-25">
        <button type="button" @click="test">测试</button>
    </div>
    
    <script type="text/javascript">
    
        var vm = new Vue({
            el: "#app-25",
            data: {
            },
            methods: {
                test: function () {
                    // 发送异步请求
                    axios
                        .all([f1(), f2()])
                        .then(axios.spread(function (res1, res2) {
                        // 两个请求都要执行完毕
                        console.log("所有请求都完成")
                        console.log(res1);
                        console.log(res2);
                    }));
                }
            }
        });
        function f1() {
            console.log('调用第一个接口')
            return axios.get("json/json_demo.json");
        }
        function f2() {
            console.log('调用第二个接口')
            return axios.get("json/json_demo2.json");
        }
    </script>
    

    注:两个请求执行完成后,才执行 axios.spread() 中的函数,且 axios.spread() 回调函数的的返回值中的请求结果的顺序和请求的顺序一致

    F12 查看控制台输出情况

    在这里插入图片描述

    11.5 箭头函数

    11.5.1 axios 回调函数的参数 res

    res 并不是接口返回的数据,而是表示一个响应数据:res.data 才表示接口响应的数据

    11.5.2 箭头函数

    <script type="text/javascript">
        var vm = new Vue({
            el: "#app-24",
            data: {
                songs: ""
            },
            methods: {
                test4: function () {
                    // 发送异步请求
                    axios
                        .get("json/json_demo2.json")
                        .then((res) => {
                        // res 并不是接口返回的数据,而是表示一个响应数据:res.data 才表示接口响应的数据
                        this.songs = res.data;
                        console.log(res.data)
                    })
                }
            }
        })
    </script>
    

    十二、 路由 router

    router 是由 vue 官方提供的用于实现组件跳转的插件。

    Vue Router 是 Vue.js (opens new window)官方的路由管理器。它和 Vue.js 的核心深度集成,让构建单页面应用变得易如反掌。

    12.1 路由插件的引用

    12.1.1 离线

    12.1.2 在线 CDN

    <script src="https://unpkg.com/vue/dist/vue.js"></script>
    <script src="https://unpkg.com/vue-router/dist/vue-router.js"></script>
    

    当你要把 Vue Router 添加进来,我们需要做的是,将组件 (components) 映射到路由 (routes),然后告诉 Vue Router 在哪里渲染它们。

    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>Title</title>
        <style type="text/css">
            body {
                padding: 0px;
                margin: 0px;
            }
            ul {
                list-style: none;
            }
            ul li {
                display: inline;
                float: left;
                margin-left: 15px;
            }
    
        </style>
        <script src="https://unpkg.com/vue/dist/vue.js"></script>
        <script src="https://unpkg.com/vue-router/dist/vue-router.js"></script>
    </head>
    <body>
        <div id="app-26">
            <div style="width: 100%; height: 70px; background: #00BFFF;">
                <table>
                    <tr>
                        <td>
                            <img src="img/1.jpg" height="70" style="margin-left: 100px;" />
                        </td>
                        <td>
                            <ul>
                                <li>
                                    <router-link to="/index">首页</router-link>
                                </li>
                                <li>
                                    <router-link to="/java">Java</router-link>
                                </li>
                                <li>
                                    <router-link to="/python">Python</router-link>
                                </li>
                                <li>
                                    <router-link to="/vue">Vue</router-link>
                                </li>
                            </ul>
                        </td>
                    </tr>
                </table>
            </div>
            <div style="width: 100%; height: 680px; background: salmon;">
                <router-view></router-view>
            </div>
        </div>
    
        <script type="text/javascript">
            <!-- vue 的路由旨在为单页面应用开发提供便携 -->
            // 定义链接跳转的模板(组件)
            const t1 = {
                template: `<p align="center">index</p>`
            };
            const t2 = {
                template: `<p align="center" >Java</p>`
            };
            const t3 = {
                template: `<p align="center">Python</p>`
            };
            const t4 = {
                template: `<p align="center">Vue</p>`
            };
            const my_router = new VueRouter({
               routes: [
                   {
                       path: '/index',
                       component: t1
                   },
                   {
                       path: '/java',
                       component: t2
                   },
                   {
                       path: '/python',
                       component: t3
                   },
                   {
                       path: '/vue',
                       component: t4
                   }
               ]
            });
            var vm = new Vue({
               el: '#app-26',
                router: my_router
            });
        </script>
    
    </body>
    </html>
    

    点击链接,根据路由,跳转并显示对应的组件模板

    在这里插入图片描述

    在这里插入图片描述

    12.2 动态路由匹配

    12.2.1 通配符

    * 可以匹配任意路径

    例如:

    • /user-* 匹配所有以 user-开头的任意路径
    • /* 匹配所有路径
    const my_router = new VueRouter({
        routes: [
            {
                path: '/user-*',
                component: t4
            },
            {
                path: '/*',
                component: t5
            }
        ]
    });
    

    注意:如果使用通配符定义路径,需要注意路由声明的顺序

    12.2.2 路由参数

    • /index/:id 可以匹配/index/开头的路径
    <div id="app-27">
    	<router-link to="/index/101">首页</router-link>
    	<router-view></router-view>
    </div>
    
    <script type="text/javascript">
        <!-- vue 的路由旨在为单页面应用开发提供便携 -->
        // 1. 定义链接跳转的模板(组件)
        const t1 = {
            template: `<p align="center">index {{$route.params.id}}</p>`
        };
        
        // 2. 定义路由
        const my_router = new VueRouter({
            routes: [
                {
                    path: '/index/:id',
                    component: t1
                }
            ]
        });
        // 3. 引用路由
        var vm = new Vue({
            el: '#app-27',
            router: my_router
        });
    </script>
    

    在这里插入图片描述

    12.2.3 优先级

    如果一个路径匹配了多个路由,则按照路由的配置顺序:路由定义的越早优先级就越高。

    12.3 嵌套路由

    在一级路由的组件中显示二级路由

    <div id="app-28">
        <div style="width: 100%; height: 20px; background: #00BFFF;">
            <router-link to="/index">首页</router-link>
            <router-link to="/index/t2">首页-t2</router-link>
            <router-link to="/index/t3">首页-t3</router-link>
            <router-view></router-view>
        </div>
    </div>
    
    <script type="text/javascript">
        <!-- vue 的路由旨在为单页面应用开发提供便携 -->
        // 1. 定义链接跳转的模板(组件)
        const t1 = {
            template: `<div style="width: 400px; height: 200px; border: blue 1px solid" >
                        index
                        <hr />
                        <router-view></router-view>
        </div>`
        };
        const t2 = {
            template: `<div>t2</div>`
        };
        const t3 = {
            template: `<div>t3</div>`
        };
    
        // 2. 定义路由
        const my_router = new VueRouter({
            routes: [
                {
                    path: '/index',
                    component: t1,
                    children: [
                        {
                            path: "t2",
                            component: t2
                        },
                        {
                            path: "t3",
                            component: t3
                        }
                    ]
                },
    
            ]
        });
        // 3. 引用路由
        var vm = new Vue({
            el: '#app-28',
            router: my_router
        });
    </script>
    

    12.4 编程式导航

    12.4.1 push()

    <div id="app-29">
        <div style="width: 100%; height: 20px; background: #00BFFF;">
            <!-- <router-link to="/index">首页</router-link> -->
            <button type="button" @click="test">首页按钮</button>
            <router-view></router-view>
        </div>
    </div>
    
    <script type="text/javascript">
        <!-- vue 的路由旨在为单页面应用开发提供便携 -->
        // 1. 定义链接跳转的模板(组件)
        const t1 = {
            template: `<div style="width: 400px; height: 200px; border: blue 1px solid" >
                        index
        </div>`
        };
    
    
        // 2. 定义路由
        const my_router = new VueRouter({
            routes: [
                {
                    path: '/index',
                    component: t1
                }
            ]
        });
        // 3. 引用路由
        var vm = new Vue({
            el: '#app-29',
            router: my_router,
            methods: {
                test: function () {
                    // js 代码实现路由跳转,编程式导航
                    my_router.push("/index");
                }
            }
        });
    </script>
    

    12.4.2 push() 参数

    // 1. 字符串
    my_router.push("/index");
    
    // 2. 对象
    my_router.push({path: "/index"});
    
    // 3. 命名的路由 name 参数指的是定义路由时指定的名字
    my_router.push({name: "r1", params: {id: 101}});
    
    // 4. URL 传值,相当于 /index?id=101
    my_router.push({path: "/index", query: {id: 101}});
    

    12.4.3 replace()

    功能与 push() 一致,区别在于 replace() 不会向 history 添加新的浏览记录

    12.4.4 go()

    参数为一个整数,表示在浏览器历史记录中前进或后退多少步 相当于 windows.history.go(-1) 的作用

    12.5 命名路由

    命名路由:在定义路由的时候可以给路由指定 name,我们在进行路由导航时可以通过路由的名字导航

     <div id="app-30">
         <div style="width: 100%; height: 20px; background: #00BFFF;">
             <input type="text" v-model="rName" />
             <router-link :to="{name: rName}">t1</router-link>
             <button type="button" @click="test">首页按钮2</button>
             <router-view></router-view>
         </div>
    </div>
    
    <script type="text/javascript">
        <!-- vue 的路由旨在为单页面应用开发提供便携 -->
        // 1. 定义链接跳转的模板(组件)
        const t1 = {
            template: `<div style="width: 400px; height: 200px; border: blue 1px solid" >
                        t1
        </div>`
        };
        const t2 = {
            template: `<div style="width: 400px; height: 200px; border: blue 1px solid" >
                        t2
        </div>`
        };
    
    
        // 2. 定义路由
        const my_router = new VueRouter({
            routes: [
                {
                    path: '/index',
                    name: "r1",
                    component: t1
                },
                {
                    path: '/index2',
                    name: "r2",
                    component: t2
                }
            ]
        });
        // 3. 引用路由
        var vm = new Vue({
            el: '#app-30',
            data: {
                rName: "r1"
            },
            router: my_router,
            methods: {
                test: function () {
                    // js 代码实现路由跳转,编程式导航
                    my_router.push({name: vm.rName});
    
                }
            }
        });
    </script>
    

    12.6 命名视图

    <div id="app-31">
        <div style="width: 100%; height: 20px; background: #00BFFF;">
            <router-link to="/index">t1</router-link>
            <router-link to="/index2">t2</router-link>
            <!-- 路由视图 -->
            <!-- 如果在 HTML 中有一个以上的路由视图 router-view,需要给 router-view 指定 name,
    在路由中需要使用 components 映射多个组件根据 name 设置组件与 router-view 的绑定关系 -->
            <router-view name="v1"></router-view>
            <router-view name="v2"></router-view>
        </div>
    </div>
    
    <script type="text/javascript">
        <!-- vue 的路由旨在为单页面应用开发提供便携 -->
        // 1. 定义链接跳转的模板(组件)
        const t11 = {
            template: `<div style="width: 400px; height: 200px; border: blue 1px solid" >
                        t11
        </div>`
        };
        const t12 = {
            template: `<div style="width: 400px; height: 200px; border: red 1px solid" >
                        t12
        </div>`
        };
        const t21 = {
            template: `<div style="width: 400px; height: 200px; border: yellow 1px solid" >
                        t21
        </div>`
        };
        const t22 = {
            template: `<div style="width: 400px; height: 200px; border: wheat 1px solid" >
                        t22
        </div>`
        };
    
    
        // 2. 定义路由
        const my_router = new VueRouter({
            routes: [
                {
                    path: '/index',
                    components: {
                        v1: t11,
                        v2: t12
                    }
                },
                {
                    path: '/index2',
                    components: {
                        v1: t21,
                        v2: t22
                    }
                }
            ]
        });
        // 3. 引用路由
        var vm = new Vue({
            el: '#app-31',
            data: {
                rName: "r1"
            },
            router: my_router,
            methods: {
                test: function () {
                    // js 代码实现路由跳转,编程式导航
                    my_router.push({name: vm.rName});
    
                }
            }
        });
    </script>
    
    

    12.7 重定向

    12.7.1 重定向

    访问 /index, 重定向到 /login

    <div id="app-32">
        <router-link to="/login">登录</router-link>
        <router-link to="/index">首页</router-link>
        <router-view></router-view>
    </div>
    
    <script type="text/javascript">
        <!-- vue 的路由旨在为单页面应用开发提供便携 -->
        // 1. 定义链接跳转的模板(组件)
        const t1 = {
            template: `<div style="width: 400px; height: 200px; border: blue 1px solid" >
                        登录
        </div>`
        };
        // 2. 定义路由
        const my_router = new VueRouter({
            routes: [
                {
                    path: '/login',
                    component: t1
                },
                {
                    path: '/index',
                    redirect: "/login"
                }
            ]
        });
        // 3. 引用路由
        var vm = new Vue({
            el: '#app-32',
            router: my_router
        });
    </script>
    
    • 根据路由命名重定向
    // 2. 定义路由
    const my_router = new VueRouter({
        routes: [
            {
                path: '/login',
                name: "r1",
                component: t1
            },
            {
                path: '/index',
                // 根据路由路径重定向
                // redirect: "/login"
                // 根据路由命名重定向
                redirect: {name: "r1"}
            }
        ]
    });
    

    12.7.2 路由别名

    <div id="app-32">
        <router-link to="/login">登录</router-link><br />
        <router-link to="/alias-login">(别名)-登录</router-link> <br />
        <router-view></router-view>
    </div>
    
    <script type="text/javascript">
        const t1 = {
            template: `<div style="width: 400px; height: 200px; border: blue 1px solid" >
                        登录
        </div>`
        };
        // 2. 定义路由
        const my_router = new VueRouter({
            routes: [
                {
                    path: '/login',
                    alias: "/alias-login",
                    component: t1
                }
            ]
        });
        // 3. 引用路由
        var vm = new Vue({
            el: '#app-32',
            router: my_router
        });
    </script>
    

    12.8 路由组件传参

    可以通过 /url/:attr 方式实现通过路由传值给组件

    <div id="app-33">
        <router-link to="/login/101">登录</router-link><br />
        <router-view></router-view>
    </div>
    
    <script type="text/javascript">
        const t1 = {
            template: `<div style="width: 400px; height: 200px; border: blue 1px solid" >
                        登录:{{$route.params.id}}
        </div>`
        };
        // 2. 定义路由
        const my_router = new VueRouter({
            routes: [
                {
                    path: '/login/:id',
                    component: t1
                }
            ]
        });
        // 3. 引用路由
        var vm = new Vue({
            el: '#app-33',
            router: my_router
        });
    </script>
    

    通过 props 传参

     <div id="app-33">
         <router-link to="/index/102">首页t2</router-link><br />
         <router-view></router-view>
    </div>
    
    <script type="text/javascript">
        const t2 = {
            props:["id"],
            template: `<div style="width: 400px; height: 200px; border: blue 1px solid" >
                        首页t2:{{id}}
        </div>`
        };
        const my_router = new VueRouter({
            routes: [
                {
                    path: '/index/:id',
                    component: t2,
                    props: true
                }
            ]
        });
        // 3. 引用路由
        var vm = new Vue({
            el: '#app-33',
            router: my_router
        });
    </script>
    
    

    在这里插入图片描述

    展开全文
  • 千锋实训第三周总结

    千次阅读 2019-07-20 14:29:45
    搭建拍卖网站后台 这周感觉又回到了第一周的节奏中----复习javaweb的常用技能,像JSTL、Jquery、Servlet这些必备技能,与第一周不同的是这个老师讲课速度还可以,第一周的老师(跟第三周的老师不是同一个)讲的是购物...

    搭建拍卖网站后台

    这周感觉又回到了第一周的节奏中----复习javaweb的常用技能,像JSTL、Jquery、Servlet这些必备技能,与第一周不同的是这个老师讲课速度还可以,第一周的老师(跟第三周的老师不是同一个)讲的是购物商城,还差支付模块没有讲完就结束了(项目还差支付模块,而且没有讲到性能优化)。第三周老师虽然没有使用任何框架,但好歹讲完了(捂脸笑哭)。附上github:

    https://github.com/zxcvbnm3618271/auctionWebSide

    展开全文
  • 本课程介绍了EasyUI常用控件的使用,EasyUI操作简单,能快速实现页面布局和元素操作,适合开发网站管理后台。 资源太大,传百度网盘了,链接在附件中,有需要的同学自取。
  • 【Python】2019千锋Python全套视频教程,史上最经典(193集)2019版-千锋Python全套-视频Week1(39集)day1(9集)视频01-python简介.wmv02-python特点.wmv03-安装与配置.wmv04-pip包管理命令.wmv05-安装问题总结.wmv06-第...
  • 许多成功的网站和APP都基于Django。Django是一个开放源代码的Web应用框架,由Python写成。通过这一章节学习,可以掌握DJango开发流程,理解DJango中的MTV模式,利用Django开发企业级电商类的项目。 第四章: Tornado...
  • OSI模型 第十六章:文件服务 FTP Server 下载文件 FTP Server启动上传功能 NFS 第十七章:网站服务 概念 第二章:用户与用户组 用户管理 命令的选项可以在Linux命令大全查找 1、创建用户 useradd [选项] 用户名 选项...
  • 千锋网络安全学习笔记部分3

    千次阅读 2021-12-12 19:15:28
    多个网页的集合就是网站。 3.web容器 (1)web容器也叫web服务器,主要提供web服务,也就是常说的http服务。 (2)常见的web容器有:Apache / IIS / Nginx等。 Apache(自带)支持.php  IIS(自带)支持.net。能...
  • 千锋Day1

    2020-03-16 22:07:54
    一:网站 网址(域名) www.taobao.com 资源存储空间(租用空间)【服务器】 项目制作 a. 规划网站(资源、功能…)[产品] b. 网站的设计(界面、交互…)[UI] c. 前端 d. 后端 e. 联调、测试 f.上线 推广 ...
  • flask框架的高级课程,带你玩转web开发领域,网站后台的搭建,APP接口的开发。扣丁学堂Python技术交流群:279521237。 资源太大,传百度网盘了,链接在附件中,有需要的同学自取。
  • 千锋学习48天:css

    2020-04-08 22:44:51
    今日千锋练习 !DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title></title> <style > html{ height: 100%; } body{ height: 100%; ...
  • B站千锋教育CSS基础语法CSS样式的引入方式CSS中的颜色表示法CSS背景样式CSS边框样式CSS文字样式CSS段落样式CSS复合样式CSS选择器CSS样式继承CSS优先级CSS盒子模型标签分类显示框类型标签嵌套规范overflow溢出隐藏...
  • 参考视频:【千锋教育】网络安全工程师 WEB服务器 1、WEB服务器(也称网页服务器、HTTP服务器)一般指网站服务器,是指驻留于因特网上某种类型计算机的程序,可以处理浏览器等Web客户端的请求并返回相应响应,也...
  • 许多成功的网站和APP都基于Django。Django是一个开放源代码的Web应用框架,由Python写成。通过这一章节学习,可以掌握DJango开发流程,理解DJango中的MTV模式,利用Django开发企业级电商类的项目。 第四章: xa0...
  • 许多成功的网站和APP都基于Django。Django是一个开放源代码的Web应用框架,由Python写成。通过这一章节学习,可以掌握DJango开发流程,理解DJango中的MTV模式,利用Django开发企业级电商类的项目。 第四章: Tornado...
  • 千锋学习’

    2021-12-17 19:01:03
    数据库的出现 静态网页与脚本都是事前设计好的,- 般不经常改动,但网站上很多内容需要经常的更新,如新闻、博客文章、互动游戏等,这些变动的数据放在静态的程序中显然不适合,传统的办法是数据与程序分离,采用...
  • 千锋带你学习强大的Laravel框架以国内动态网站来说,超过80%都在使用PHP技术,少数普通PHP程序员无论从数量还是质量上都无法满足庞大的市场需求,在一个信息科技快速发展的时代,自然需要PHP的快速开发来实现也就说PHP是...
  • 动态WEb网站搭建 在IDEA下如何修改默认启动访问路径 点击右上角tomcat,选中Edit Configurations,选择Deployment后修改Application context即可修改默认启动访问路径。 tomcat项目部署原理 tomcat部署项目有三种...
  • 千锋Django学习笔记

    2022-01-14 08:43:25
    千锋Django学习笔记 文章目录千锋Django学习笔记写在前面1. MVC和MTV2. Django简介3. MTV简单流程4. 和Model的简单对接5. Model6. Template7. View8. 会话9. 迁移原理和模型关系10. 静态资源11. 缓存12. 中间件和AOP...
  • 立即学习:https://edu.csdn.net/course/play/30980/458362?utm_source=blogtoedu 网页:html + css+js+jquery+bootstrap VUE:前后分离 web后端:网站 联合项目:h5+python 触发事件--》向后端发请求--》后端做处理
  • 它附带了许多完全可定制的模块化和灵活组件,您可以使用这些组件设计在任何设备上都令人惊叹的漂亮响应网站。通过Web前端培训的学习,理论知识+实践项目,双管齐下,更有利于学员加深对所学知识的理解和运用,真正...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 4,063
精华内容 1,625
关键字:

千锋网站