Vue框架的介紹及使用


Vue框架

定義:漸進式 JavaScript 框架

漸進式:可以控制一個頁面的一個標簽,可以控制一系列標簽,也可以控制整個頁面,甚至可以控制整個前台項目。

通過對框架的了解與運用程度,來決定其在整個項目中的應用范圍,最終可以獨立以框架方式完成整個web前端項目

一、Vue基礎

1、什么是Vue

可以獨立完成前后端分離式web項目的JavaScript框架

2、為什么要學習Vue

三大主流框架之一:Angular(龐大) React(精通移動端) Vue(吸取前兩者優勢,輕量級)

先進的前端設計模式:MVVM

可以完全脫離服務器端,以前端代碼復用的方式渲染整個頁面:組件化開發

3、特點

有指令(分支結構,循環結構...),復用頁面結構等

有實例成員(過濾器,監聽),可以對渲染的數據做二次格式化

有組件(模塊的復用或組合),快速搭建頁面

 

單頁面web應用

數據驅動

數據的雙向綁定

虛擬DOM

4、Vue安裝

5、Vue環境簡單搭建:通過script標簽導入vue文件即可

"""
1)cdn導入
<script src="https://cn.vuejs.org/js/vue.js"></script>

2)本地導入
<script src="js/vue.js"></script>
"""

注意:

掛載點介紹

el: 掛載點
1)一個掛載點只能控制一個頁面結構(優先匹配到的結構)
2)掛載點掛載的頁面標簽嚴格建議用id屬性進行匹配(一般習慣用app)
3)html標簽與body標簽不能作為掛載點(html和body標簽不可以被替換,組件中詳細介紹)
4)是否接受vue對象,是外界是否要使用vue對象的內容決定的

<!DOCTYPE html>
<html lang="zh">
<head>
    <meta charset="UTF-8">
    <title>掛載點</title>

<body>
    <div id="app">
        <div>
            {{ num }}
        </div>
        <div>
            {{ num }}
        </div>
    </div>
    <div id="main">
        {{ n }}
    </div>
</body>
<script src="js/vue.js"></script>
<script>
    var app = new Vue({
        el: '#app',
        data: {
            num:100
        }
    });
    console.log('12345');
    console.log(app.num);
    // console.log(app.$data.num);
    console.log(app.$el);

    new Vue({
        el: '#main',
        data:{
            n:app.num
        }
    })
</script>
</html>
掛載點el

插值表達式

1)空插值表達式:{{ }}
2)插值表達式中渲染的變量在data中可以初始化
3)插值表達式可以進行簡單運算與簡單邏輯
4)解決插值表達式符號沖突,用delimiters自定義(了解)

<!DOCTYPE html>
<html lang="zh">
<head>
    <meta charset="UTF-8">
    <title>插值表達式</title>

</head>
<body>
    <div id="app">
        <p>{{ info }}</p>
        <p>{{ msg }}</p>
        <p>{{ }}</p>
        <p>{{ num }}</p>
        <p>{{ num + 10 * 2 }}</p>
        <p>{{ msg + num }}</p>
        <p>{{ msg.length + num }}</p>
        <p> {{ msg[4] }}</p>
        <p> {{ msg.split('') }}</p>
<!--        <p>[{ num }]</p>-->
    </div>
</body>
<script src="js/vue.js"></script>
<script>
    new Vue({
        el: '#app',
        data:{
            info:'信息',
            msg:'message',
            num:10
        },
        // 控制vue插值表達式符號 (了解)
        // delimiters: ['[{','}]']
    })
</script>
</html>
插值表達式例子

過濾器

1)用實例成員filters來定義過濾器
2)在頁面結構中,用 | 來標識使用過濾器
3)過濾方法的返回值就是過濾器過濾后的結果
4)過濾器可以對1~n個變量進行過濾,同時還可以傳入輔助的變量,
過濾器方法接受參數是按照傳入的位置先后

計算屬性

"""
計算屬性:
1)即vue中的方法屬性,就是方法名可以作為屬性來使用,屬性值為方法的返回值
2)在computed中聲明的方法屬性,不能在data中重復聲明,只是比data中聲明的屬性要多出寫邏輯的地方
3)方法屬性自帶監聽機制,在方法屬性中出現的變量都會被監聽,一旦有任何被監聽的變量值發生更新,方法屬性都會被調用,更新方法屬性的值
4)方法屬性一定要在頁面中渲染一次,方法屬性才有意義,多次渲染 方法屬性只會被調用一次

應用場景:計算器,一個變量依賴於多個變量,且需要進行一定的邏輯運算

"""
<div id="app">
    <!-- type="number"表示只能寫數字 -->
    <input type="number" v-model="num1">
    +
    <input type="number" v-model="num2">
    =
    <button>{{ sum }}</button>
</div>
<script>
    new Vue({
        el: '#app',
        data: {
            // sum: '',  // 重復聲明
            num1: '',
            num2: '',
        },
        computed: {
            sum () {
                // num1和num2都在該方法屬性中,所以有一個更新值,該方法都會被調用
                if (this.num1 && this.num2) {
                    return +this.num1 + +this.num2;  // +this.num1是將字符串快速轉換成數字
                }
                return '結果';
            }
        }
    })
</script>
簡單計算案例

監聽屬性

"""
1)watch中不定義屬性,只是監聽屬性,所以方法的返回值沒有任何意義,只是監聽變量值是否發生更新
2)watch中的方法名,就是被監聽的屬性(方法名同被監聽屬性名)
3)被監聽的變量值一旦發生更新,監聽方法就會被調用
應用場景:
     i)k線圖:股票數據變化,頁面的k線圖重新渲染(需要邏輯將數據轉換為圖形)
     ii)拆分姓名:錄入姓名,拆分為姓和名(需要邏輯將一個數據拆分為多個數據)
"""
<div id="app">
    姓名:<input type="text" v-model="full_name">
    <hr>
    姓:<button>{{ first_name }}</button>
    名:<button>{{ last_name }}</button>
</div>
<script>
    new Vue({
        el: '#app',
        data: {
            full_name: '',
            first_name: '未知',
            last_name: '未知'
        },
        watch: {
            full_name () {
                if (this.full_name) {
                    // 實現簡易的拆分邏輯
                    this.first_name = this.full_name.split('')[0];
                    this.last_name = this.full_name.split('')[1];
                } else {
                    this.first_name = '未知';
                    this.last_name = '未知';
                }
            }
        }
    })
</script>
姓名拆分案例

JS反引號變量占位

"""
1)雙引號:
    "前綴" + 變量 + "后綴"
    
2)單引號:
    '前綴' + 變量 + '后綴'

3)反引號:
    `前綴${變量}后綴`
    注:在反引號中可以用 ${} 來包裹變量,實現字符串拼接
"""

基礎實例成員

1)el:掛載點
2)data:提供渲染的數據
3)methods:提供綁定的方法
4)filters:提供自定義過濾器,過濾器可以同時過濾多個參數,還可以串聯過濾器
5)delimiters:插值表達式標識符,['{{','}}'] 
6)computed:計算(方法屬性)
7)props:屬性
8)watch:監聽

指令

文本指令

1)v-* 是vue指令,會被vue解析,v-text="num"中的num是變量(指令是有限的,不可以自定義)

2)v-text是原樣輸出渲染內容,渲染控制的標簽自身內容會被替換掉(<p v-text="num">123</p>會被num替換)

3)v-html可以解析渲染html語法的內容

<!DOCTYPE html>
<html lang="zh">
<head>
    <meta charset="UTF-8">
    <title>文本指令</title>

</head>
<body>
    <div id="app">
        <p>{{ num | add(300) }}</p>
        <p v-text="num" class="123"></p>
        <p v-text="num">123</p>
        <p v-text="info"></p>
        <p v-html="info"></p>

        <!-- js基本數據類型:字符串、數字、布爾、undefined -->
        <p v-text="'abc' + num + 10"></p> <!-- abc10010 -->
        <p>{{ 'abc' + num + 10 }}</p>
    </div>
</body>
<script src="js/vue.js"></script>
<script>
    new Vue({
        el: '#app',
        data: {
            num:100,
            info: '<i>info內容</i>'
        },
        filters:{
            add:function (a,b) {
                return a + b;
            }
        }
    })
</script>
</html>
v-text指令

 事件指令

"""
/**
 * 一、數據驅動
 *  1)操作是一個功能,使用需要一個方法來控制 2)方法名是變量,所以控制變量就可以控制該方法
 *
 *
 * 二、事件指令
 *  1)在實例成員methods中聲明事件方法
 *  2)標簽通過事件指令綁定聲明的方法: v-on:事件名="事件方法名"
 *      eg: <button v-on:click="btnClick">按鈕</button>
 *  3)標簽通過事件指令綁定聲明的方法,且自定義傳參: v-on:事件名="事件方法名()"
 *      eg: <button v-on:click="btnClick()">按鈕</button>  不傳任何參數
 *      eg: <button v-on:click="btnClick($event)">按鈕</button>  傳入事件對象,同不寫()
 *      eg: <button v-on:click="btnClick(10)">按鈕</button>  只傳入自定義參數,當然也可以傳入事件對象
 */
"""

重點:v-on: 可以簡寫為 @
 
<body>
    <div id="app">
        <button v-on:click="btnClick">{{ btn1 }}</button>

        <button v-on:click="btnClick">{{ btn2 }}</button>
        <hr>

        <!-- 直接綁定事件名:系統會在觸發事件時(點擊時)調用事件方法(fn1),傳給事件方法一個參數(事件對象) -->
        <button v-on:click="fn1">按鈕3</button>

        <!-- 綁定的事件名后跟着(),不是主動調用事件方法,而是表示在觸發事件調用時,傳入的參數全由用戶自己決定 -->
        <button v-on:click="fn2($event, 10, 20)">按鈕4</button>

        <hr>
        <button v-on:click="fn(btn1)">{{ btn1 }}</button>

        <button v-on:click="fn(btn2)">{{ btn2 }}</button>
    </div>
</body>
<script src="js/vue.js"></script>
<script>
    // 對比DOM驅動:1)js選擇器獲取目標標簽 2)為目標標簽綁定事件 3)在事件中完成相應邏輯
    // var btn = document.getElementsByTagName('button')[0];
    // btn.onclick = function () {
    //     console.log(111111111111);
    // };
    new Vue({
        el: '#app',
        data: {
            btn1: '按鈕1',
            btn2: '按鈕2',
        },
        methods: {
            btnClick () {
                console.log(666)
            },
            fn1 (ev) {
               console.log(ev.clientX, ev.clientY);
            },
            fn2(ev, n1, n2) {
                console.log(ev, n1, n2);
                console.log(ev.clientX, ev.clientY);
            },
            fn (msg) {
                console.log(msg);
            }
        }
    })
</script>
view.code
<style>
    body {
        /* 不允許文本選中 */
        user-select: none;
    }
    .d1:hover {
        color: orange;
        /* 鼠標樣式 */
        cursor: pointer;
    }
    /* 只有按下采用樣式,抬起就沒了 */
    .d1:active {
        color: red;
    }
    /* div標簽壓根不支持 :visited 偽類 */
    .d1:visited {
        color: pink;
    }

    .d2.c1 {
        color: orange;
    }
    .d2.c2 {
        color: red;
    }
    .d2.c3 {
        color: pink;
    }
</style>
<div id="app">
    <div class="d1">偽類操作</div>
    <br><br><br>
    <!--
    click: 單擊
    dblclick:雙擊
    mouseover:懸浮
    mouseout:離開
    mousedown:按下
    mouseup:抬起
    -->
    <div :class="['d2', c]" @click="hFn('c1')" @mouseover="hFn('c2')" @mousedown="hFn('c3')">事件處理</div>
</div>
<script>
    new Vue({
        el: '#app',
        data: {
            c: '',
        },
        methods: {
            hFn (c) {
                this.c = c
            }
        }
    })
</script>
事件補充

斗篷指令

v-cloak:避免屏幕閃爍

1)屬性選擇器,會將v-cloak屬性所在的標簽隱藏
2)當vue環境加載后,會將v-cloak屬性解析移除,所以內容{{ num }}就會顯示出來
3)而現在vue已經准備完畢,所以用戶會直接看到數值10,而不會看到 頁面從{{ num }}閃爍成數值10 """

<!DOCTYPE html>
<html lang="zh">
<head>
    <meta charset="UTF-8">
    <title></title>
    <style>
        [v-cloak] {
            display: none;
        }
    </style>
</head>
<body>
    <div id="app" v-cloak>
        <p>{{ num }}</p>
    </div>
</body>
<script src="js/vue.js"></script>
<script>
    new Vue({
        el: '#app',
        data:{
            num:10
        },
    })
</script>
</html>
View Code

屬性指令

屬性指令
1)語法:v-bind:屬性名="變量"
2)針對不同屬性,使用方式稍微有區別
    i)自定義屬性以及title這些,直接賦值的,使用方式如下(t是變量,'o'是常量)
         <p v-bind:title="t" v-bind:owen="'o'">段落</p>
    ii)class屬性(重點):
         綁定的變量:值可以為一個類名 "p1",也可以為多個類名 "p1 p2"
         綁定的數組:數組的每一個成員都是一個變量
         綁定的字典:key就是類名,value是決定該類名是否起作用的
   iii)style屬性(了解):
      綁定的變量:值是一個字典
重點:v-bind: 可以簡寫為 :
<!DOCTYPE html>
<html lang="zh">
<head>
    <meta charset="UTF-8">
    <title>屬性指令</title>
    <style>
        .b1 {
            width: 100px;
            height: 100px;
            background-color: red;
        }
        .b2 {
            border-radius: 50%;
        }
    </style>
</head>
<body>
    <!--1) 標簽的屬性沒有被v-bind綁定,就是同原來一樣基本使用-->
    <!--2)標簽的屬性被v-bind綁定,就會被vue控制,值就會變為變量-->
    <!-- 換而言之,如果一個屬性要被vue控制,填寫變量就要用v-bind來處理-->
    <div id="app">
        <p v-bind:class="a" style="color: red;background-color:orange " v-bind:title="t" v-bind:owen="'o'">段落</p>
        <p v-bind:class="b"></p>
        <p class="b1 b2"></p>
        <p v-bind:class="[c,d]"></p>
        <p v-bind:class="{b1:0}"></p>
        <!--
        a是變量,值就是類名
        b1就是類名,不是變量
        e是變量,值為布爾,決定b1類是否起作用
        -->
        <p v-bind:class="[a,{b1:e}]"></p>
    </div>
</body>
<script src="js/vue.js"></script>
<script>
    new Vue({
        el: '#app',
        data:{
            t:'懸浮提示',
            a:'a1',
            b:'b1 b2',
            c:'b1',
            d:'b2',
            e:true,
        }
    })
</script>
</html>
<p v-bind:style="myStyle"></p>
<script>
    let app = new Vue({
        el: '#app',
        data: {
            myStyle: {
                width: '50px',
                height: '50px',
                backgroundColor: 'pink',
                borderRadius: '50%'
            }
        },
    })
</script>

案例:

<style>
    .live{
        background-colorL:yellowgreen
    }
</style>

<button v-bind:class="{live: isLive == 1}" v-on:click="changeLive(1)">1</button>
<button v-bind:class="{live: isLive == 2}" v-on:click="changeLive(2)">2</button>
<button v-bind:class="{live: isLive == 3}" v-on:click="changeLive(3)">3</button>
<script>
    let app = new Vue({
        el: '#app',
        data: {
            isLive: 0,
        },
        methods: {
            changeLive (index) {
                // this就代表當前vue對象,和app變量等價
                // app.isLive = index;
                this.isLive = index;
            }
        }
    })
</script>  
View Code

表單指令

1)語法:v-model="變量"
2)v-model綁定的變量控制的是表單元素標簽的value屬性值
3)v-model要比v-bind:value要多一個監聽機制
4)數據的雙向綁定:
    v-model可以將綁定的變量值映射給表單元素的value
    v-model還可以將表單元素的新value映射給表單的變量
<!-- 兩個輸入框內容會同時變化 -->
<div id="app">
    <form action="" method="">
        <input name="n1" type="text" v-model="v1">
        <input name="n2" type="text" v-model="v1">
        <button type="submit">提交</button>
    </form>
</div>
<script>
    new Vue({
        el: '#app',
        data: {
            v1: ''
        }
    })
</script>

條件指令

1)語法:v-show="變量" | v-if="變量"
2)兩者區別:
         v-show在隱藏標簽時,采用display:none渲染標簽,標簽通過css隱藏
         v-if在隱藏標簽時,不會渲染到頁面上
3)v-if有家族:v-if | v-else-if | v-else
        v-if是必須的,必須設置條件
        v-else-if可以為0~n個,必須設置條件
        v-else可以為0~1個
       上方分支成立會屏蔽下方所有分支,從上到下依次類推
     
    <div id="app">
        <div>
            <p v-show="isShow">show控制顯隱</p>
            <p v-if="isShow">if控制顯隱</p>
        </div>

        <div>
            <p v-if="1">你是第一個p</p>
            <p v-else-if="2">你是第二個p</p>
            <p v-else>你是第三個p</p>
        </div>
    </div>
    <script>
        new Vue({
            el: '#app',
            data:{
                isShow:false,
            }
        })
    </script>

案例:

<!DOCTYPE html>
<html lang="zh">
<head>
    <meta charset="UTF-8">
    <title>案例</title>
<style>
    body {
        margin: 0
    }
    button {
        width: 60px;
        line-height: 40px;
        float: right;
    }
    .bGroup:after {
        display: block;
        content: '';
        clear: both;
    }
    .box {
        /* vw: view width  vh: view height*/
        width: 100vw;
        height: 200px;
    }
    .red {
        background-color: red;
    }
    .green {
        background-color: green;
    }
    .blue {
        background-color: blue;
    }

    button.active {
        background-color: cyan;
    }
</style>

</head>
<body>
    <div id="app">
        <div class="bGroup">
            <button :class="{active: isShow === 'red'}" @click="isShow = 'red'"></button>
            <button :class="{active: isShow === 'green'}" @click="isShow = 'green'"></button>
            <button :class="{active: isShow === 'blue'}" @click="isShow = 'blue'"></button>
        </div>
        <div>
            <div v-if="isShow === 'red'" class="box red"></div>
            <div v-else-if="isShow === 'green'" class="box green"></div>
            <div v-else class="box blue"></div>
        </div>
    </div>
</body>
<script src="js/vue.js"></script>
<script>
    new Vue({
        el: '#app',
        data: {
            isShow: 'red'
        }
    })
</script>
</html>
View Code

循環指令

"""
1)語法:v-for="ele in obj"  obj是被遍歷的對象,ele是遍歷得到的每一次結果
2)遍歷可迭代對象的首要結果,都是可迭代對象容器中的值,其次還可以遍歷得到索引及鍵等數據
     字符串:v-for="v in str"  |  v-for="(v, i) in str"
     數組:v-for="v in arr"  |  v-for="(v, i) in arr"
     對象:v-for="v in obj"  |  v-for="(v, k) in obj"  |  v-for="(v, k, i) in obj"

注:v-for遍歷要依賴於一個所屬標簽,該標簽及內部所有內容會被遍歷復用
"""
<!DOCTYPE html>
<html lang="zh">
<head>
    <meta charset="UTF-8">
    <title>循環指令</title>
</head>
<body>
    <div id="app">
        <!-- 遍歷數字
        5
        【1】【2】【3】【4】【5】
        -->
        <p>{{ d1 }}</p>
        <i v-for="e in d1">【{{ e }}】</i>
        <hr>

        <!-- 遍歷字符串
        abc
        【a】【b】【c】
        【0a】【1b】【2c】
        -->
        <p>{{ d2 }}</p>
        <i v-for="e in d2">【{{ e }}】</i>
        <i v-for="(e, i) in d2">【{{ i }}{{ e }}】</i>
        <hr>

        <!-- 遍歷數組
        [ 1, 3, 5 ]
        【1】【3】【5】
        【01】【13】【25】
        -->
        <p>{{ d3 }}</p>
        <i v-for="e in d3">【{{ e }}】</i>
        <i v-for="(e, i) in d3">【{{ i }}{{ e }}】</i>
        <hr>

        <!-- 遍歷對象
        { "name": "Bob", "age": 17.5, "gender": "男" }
        【Bob】【17.5】【男】
        【name-Bob】【age-17.5】【gender-男】
        【name-Bob-0】【age-17.5-1】【gender-男-2】
        -->
        <p>{{ d4 }}</p>
        <i v-for="e in d4">【{{ e }}】</i>
        <i v-for="(e, k) in d4">【{{ k }}-{{ e }}】</i>
        <i v-for="(e, k, i) in d4">【{{ k }}-{{ e }}-{{ i }}】</i>
        <hr>

    </div>
</body>
<script>
    new Vue({
        el: '#app',
        data: {
            d1: 5,
            d2: 'abc',
            d3: [1, 3, 5],
            d4: {
                name: "Bob",
                age: 17.5,
                gender: ""
            }
        }
    })
</script>

案例:

<!DOCTYPE html>
<html lang="zh">
<head>
    <meta charset="UTF-8">
    <title></title>
    <style>
    .box {
        width: 280px;
        border: 1px solid #eee;
        border-radius: 5px;
        overflow: hidden; /* 隱藏超出父級顯示范圍外的內容 */
        text-align: center; /* 文本相關的屬性大多默認值是inherit */
        float: left;
        margin: 10px;
    }
    .box img {
        width: 100%;
    }
    </style>
</head>
<body>
    <div id="app">
        <div class="box" v-for="obj in goods">
            <img :src="obj.img" alt="">
            <p>{{ obj.title }}</p>
        </div>
    </div>
</body>
<script src="js/vue.js"></script>
<script>
    let goods = [
        {
            "img":"https://***1.jpg",
            "title": "商品1"
        },
        {
            "img":"https://***2.jpg",
            "title": "商品2"
        }
    ];

    new Vue({
        el:"#app",
        data:{
            goods,
        }
    })
</script>
</html>
View Code

todolist

補充知識點:

js的Array操作

"""
尾增:arr.push(ele)  
首增:arr.unshift(ele)
尾刪:arr.pop()
首刪:arr.shift()
增刪改插:arr.splice(begin_index, count, args)
"""

前台數據庫

"""
// 存
// 持久化化存儲,永遠保存
localStorage.name = "Bob";
// 持久化化存儲,生命周期同所屬標簽(頁面),頁面關閉,重新打開就會丟失
sessionStorage.name = "Tom";

// 取
console.log(localStorage.name);
console.log(sessionStorage.name);

// 清空
localStorage.clear();
sessionStorage.clear();

// 短板:只能存儲字符串,所以對象和數組需要轉換為json類型字符串,再進行存儲
let a = [1, 2, 3];
localStorage.arr = JSON.stringify(a);
let b = JSON.parse(localStorage.arr);
console.log(b);
"""

splice:

 

 

案例:留言板

<!DOCTYPE html>
<html lang="zh">
<head>
    <meta charset="UTF-8">
    <title>todolist</title>
    <style>
        li:hover {
            color: red;
            cursor: pointer;
        }
    </style>
</head>
<body>
    <div id="app">
        <form action="">
            <input type="text" v-model="info">
            <button type="button" @click="sendInfo">留言</button>
        </form>
        <ul>
            <li v-for="(info,index) in info_arr" @click="deleteInfo(index)">{{ info }}</li>
        </ul>
    </div>
</body>
<script src="js/vue.js"></script>
<script>
    new Vue({
        el: '#app',
        data:{
            info:'',
            // 三元運算符: 條件 ? 結果1 : 結果2
            info_arr:localStorage.info_arr ? JSON.parse(localStorage.info_arr) : []
        },
        methods: {
            sendInfo() {
                //完成留言,將info添加到info_arr
                // 增 push unshift | 刪 pop shift
                if(this.info){
                    //留言
                    this.info_arr.push(this.info);
                    //清空輸入框
                    this.info = '';
                    //前台數據持久化(緩存)
                    localStorage.info_arr = JSON.stringify(this.info_arr);

                }
            },
            deleteInfo(index){
                // 刪留言
                this.info_arr.splice(index,1)
                // 同步給數據庫
                localStorage.info_arr = JSON.stringify(this.info_arr);
            }
        }

    })
</script>
</html>
View Code

 

"""1)雙引號:"前綴" + 變量 + "后綴"2)單引號:'前綴' + 變量 + '后綴'
3)反引號:`前綴${變量}后綴`注:在反引號中可以用 ${} 來包裹變量,實現字符串拼接"""


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM