<output id="qn6qe"></output>

    1. <output id="qn6qe"><tt id="qn6qe"></tt></output>
    2. <strike id="qn6qe"></strike>

      亚洲 日本 欧洲 欧美 视频,日韩中文字幕有码av,一本一道av中文字幕无码,国产线播放免费人成视频播放,人妻少妇偷人无码视频,日夜啪啪一区二区三区,国产尤物精品自在拍视频首页,久热这里只有精品12

      二、Vue常用操作

      Vue常用操作

      Vue常用操作: https://cn.vuejs.org/v2/api/
      對Vue2的掌握,我們主要從 vue基礎(chǔ)指令、過濾器、監(jiān)聽器、計(jì)算屬性、全局組件、父子組件、組件注冊、組件之間通信、自定義事件、插槽、路由、過渡動畫、vue生命周期 開始著手。

      一、Vue指令

      • 內(nèi)容渲染指令

            內(nèi)容渲染指令用來輔助開發(fā)者渲染DOM元素的文本內(nèi)容,常用的內(nèi)容渲染指令有: v-text、{{}}、v-html、v-once、v-pre、v-clock。
            v-text:向頁面注入文本,相當(dāng)于innerText。v-html:向頁面注入元素,相當(dāng)于innerHTML。v-once:只渲染元素和組件一次,v-pre:用于跳過這個(gè)元素和它子元素的編譯過程,標(biāo)簽內(nèi)怎么編寫頁面就展示什么。v-clock:在某些情況下(例如網(wǎng)絡(luò)延遲等),我們?yōu)g覽器可能會直接顯示出未編譯的插值運(yùn)算符,也就是一閃而過看到{{}}這些雙括號的模板,我們可以采用該命令。
      <!DOCTYPE html>
      <html>
      	<head>
      		<meta charset="utf-8" />
      		<title></title>
      		<!--引入vue.js-->
      		<script src="lib/vue-2.6.12.js"></script>
      		
      		<style>
      			[v-clock] {
      				display: none;
      			}
      		</style>
      	</head>
      	<body>
      		<div id="app">
      			<!-- v-tetx相當(dāng)于innerText,把username 對應(yīng)的值渲染到第一個(gè)p標(biāo)簽中 -->
      			<p v-text="username">姓名</p>
      			
      			<!-- {{}}插值運(yùn)算把gender對應(yīng)的值渲染第二個(gè)p標(biāo)簽中-->
      			<p>性別:{{gender}}</p>
      			
      			<!-- v-html相當(dāng)于innerHTML,把包含HTML標(biāo)簽的字符串渲染到頁面上-->
      			<p v-html="hobby">愛好</p>
      			
      			<hr />
      			<!-- v-once元素和組件只會被渲染一次 -->
      			<p v-once>原始值:{{msg}}</p>
      			<p>后面值:{{msg}}</p>
      			<input type="text" v-model="msg" />
      			
      			<!-- v-pre跳過元素和子元素的編譯過程,原始展示 -->
      			<p v-pre>{{msg}}}</p>
      			
      			<!-- 解決因?yàn)榫W(wǎng)絡(luò)延遲導(dǎo)致的插值運(yùn)算值還沒有及時(shí)渲染時(shí)情況 -->
      			<p v-clock>{{msg}}</p>
      		</div>
      		
      		<script>
      			const vm = new Vue({
      				el:'#app',
      				data:{
      					username:'張三',
      					gender:'男',
      					hobby:'<font color="red">王者榮耀</font>',
      					msg:'這是一條測試消息'
      				}
      			});
      		</script>
      	</body>
      </html>
      測試結(jié)果:
      內(nèi)容渲染指令使用

      • 屬性綁定指令

         v-bind動態(tài)地綁定一個(gè)或多個(gè)特性。給一個(gè)標(biāo)簽動態(tài)綁定一個(gè)屬性、樣式、一些類,或者將一個(gè)對象綁定到一個(gè)標(biāo)簽上。鑒于v-bind使用較多,官方推薦使用簡寫 :屬性

      <!DOCTYPE html>
      <html>
      	<head>
      		<meta charset="utf-8" />
      		<title></title>
      		<!--引入vue.js-->
      		<script src="lib/vue-2.6.12.js"></script>
      		<style>
      			.active {
      				background-color: orange;
      			}
      			.fontActive {
      				font-size: 20px;
      			}
      		</style>
      	</head>
      	<body>
      		<div id="app">
      			<!-- 綁定一個(gè)屬性 ,v-bind可以簡寫-->
      			<img v-bind:src="imgSrc" height="100" width="100" />
      			<img :src="imgSrc" height="100" width="100"/>
      			<!-- 綁定一個(gè)樣式 -->
      			<p :style='{color:fontColor}'>我愛Vue</p>
      			<!-- 綁定一個(gè)類 -->
      			<p v-for="(course,index) in courses" :class='index==acticeIndex?"active":""'>
      				{{course}}
      			</p>
      			<p :class=['active',{'fontActive':bool}]>多個(gè)樣式</p>
      			<!-- 綁定一個(gè)有屬性的對象-->
      			<p v-bind="{id:1,name:'mytext'}">綁定有屬性的對象</p>
      		</div>
      		
      		<script>
      			const vm = new Vue({
      				el:'#app',
      				data:{
      					//綁定屬性
      					imgSrc:'img/1.jpeg',
      					//綁定樣式
      					fontColor:'red',
      					bool:true,
      					//綁定class
      					courses:['html','css','javascript'],
      					acticeIndex:2
      				}
      			});
      		</script>
      	</body>
      </html>
      測試結(jié)果:
      v-bind指令使用




      補(bǔ)充:vue指令中可以使用JavaScript表達(dá)式: 在 vue 提供的模板渲染語法中,除了支持綁定簡單的數(shù)據(jù)值之外,還支持 Javascript 表達(dá)式的運(yùn)算,例如

      • 事件綁定指令

          vue 提供了 v-on 事件綁定指令,用來輔助程序員為 DOM 元素綁定事件監(jiān)聽。v-on針對事件,動態(tài)綁定事件。表示形式有v-on:事件=“事件函數(shù)”或者簡寫@事件=“事件函數(shù)”,通過v-on綁定的事件處理函數(shù),需要在methods節(jié)點(diǎn)中聲明。原生DOM對象有onclikc、oninput、onkeyup等原生時(shí)間,vue相應(yīng)替換分別為:v-on:click、v-on:input、v-on:keyup。
      <!DOCTYPE html>
      <html>
      	<head>
      		<meta charset="utf-8" />
      		<title></title>
      		<!--引入vue.js-->
      		<script src="lib/vue-2.6.12.js"></script>
      		<style>
      			.active {
      				background-color: orange;
      			}
      			.fontActive {
      				font-size: 20px;
      			}
      		</style>
      	</head>
      	<body>
      		<div id="app">
       			<h3>count的值為: {{count}}</h3>
       			
       			<!-- "v-on:事件"完整寫法 -->
       			<button v-on:click="addCount">+1</button>
       			
       			<!-- "v-on:事件"簡寫形式,把v-on:簡寫為 @符號 -->
       			<!-- 如果事件處理函數(shù)中的代碼足夠簡單,只有一行代碼,則可以簡寫到行內(nèi) -->
       			<button @click="count+=1">+1</button>
      		</div>
      		
      		<script>
      			const vm = new Vue({
      				el:'#app',
      				data:{
      					count:0
      				},
      				methods:{
      					addCount(){
      						this.count+=1;
      					}
      				}
      			});
      		</script>
      	</body>
      </html>
      測試結(jié)果:

        1.綁定事件并傳參

         在使用v-on指令綁定事件時(shí),可以使用()進(jìn)行傳參,示例如下:
      綁定事件并傳參

         2.$event

          $event是vue提供的特殊變量,用來表示原生的事件參數(shù)對象event。$event可以解決事件參數(shù)對象event被覆蓋的問題,示例如 下:

      $event使用

         3.事件修飾符

         在事件處理函數(shù)中調(diào)用 event.preventDefault() 或 event.stopPropagation() 是非常常見的需求。因此,vue 提供了事件修飾符的概念,來輔助程序員更方便的對事件的觸發(fā)進(jìn)行控制。常用的 5 個(gè)事件修飾符如下:
      事件修飾符說明
      .prevent阻止默認(rèn)行為(例如:阻止a鏈接的跳轉(zhuǎn)、阻止表單的提交等)
      .stop阻止事件冒泡
      .capture以捕獲模式觸發(fā)當(dāng)前的事件處理函數(shù)
      .once綁定的事件只能觸發(fā)一次
      .self只有在event.target 是當(dāng)前元素自身時(shí)觸發(fā)事件處理函數(shù)

         4.按鍵修飾符

      在監(jiān)聽鍵盤事件時(shí),我們經(jīng)常需要判斷詳細(xì)的按鍵。此時(shí),可以為鍵盤相關(guān)的事件添加按鍵修飾符,例如:


      • 雙向綁定指令

         vue 提供了 v-model 雙向數(shù)據(jù)綁定指令,用來輔助開發(fā)者在不操作 DOM 的前提下,快速獲取表單的數(shù)據(jù)。
      為了方便對用戶輸入的內(nèi)容進(jìn)行處理,vue 為 v-model 指令提供了 3 個(gè)修飾符,分別是:
      事件修飾符 說明示例
      .number 自動將用戶的輸入值轉(zhuǎn)為數(shù)值類型<input v-model.number="age" />
      .trim 自動過濾用戶輸入的首尾空白字符<input v-model.trim="msg" />
      .lazy 在“change”時(shí)而非“input”時(shí)更新<input v-model.lazy="msg" />

      • 條件渲染指令

         條件渲染指令用來輔助開發(fā)者按需控制 DOM 的顯示與隱藏。條件渲染指令有如下兩個(gè),分別是:v-if(v-else-if、v-else)、v-show。
      <!DOCTYPE html>
      <html>
      	<head>
      		<meta charset="utf-8" />
      		<title></title>
      		<!--引入vue.js-->
      		<script src="lib/vue-2.6.12.js"></script>
      	</head>
      	<body>
      		<div id="app">
      			<div v-show="score<60">差</div>
      			<div v-show="score>=60&&score<90">良</div>
      			<div v-show="score>=90">優(yōu)秀</div>
      			
      			<!-- v-if、v-else-if、v-else相當(dāng)于if、else if、else,只會展示符合條件的元素,其他元素均移除 -->
      			<div v-if="score<60">差</div>
      			<div v-else-if="score>=60&&score<90">良</div>
      			<div v-else>優(yōu)秀</div>
      		</div>
      		
      		<script>
      			const vm = new Vue({
      				el:'#app',
      				data:{
      					score:80
      				}
      			});
      		</script>
      	</body>
      </html>
      測試結(jié)果:
      v-if和v-show區(qū)別
      v-if 和 v-show 的區(qū)別:
      實(shí)現(xiàn)原理不同:
      ? v-if 指令會動態(tài)地創(chuàng)建或移除 DOM 元素,從而控制元素在頁面上的顯示與隱藏;
      ? v-show 指令會動態(tài)為元素添加或移除 style="display: none;" 樣式,從而控制元素的顯示與隱藏;
      性能消耗不同:
      v-if 有更高的切換開銷,而 v-show 有更高的初始渲染開銷。因此:
      ? 如果需要非常頻繁地切換,則使用 v-show 較好
      ? 如果在運(yùn)行時(shí)條件很少改變,則使用 v-if 較好

      • 列表渲染指令

         v-for基于數(shù)據(jù)源多次渲染元素或者模板塊,也可以為數(shù)組索引指定別名(或者用于創(chuàng)建對象的鍵)。v-for 指令還支持一個(gè)可選的第二個(gè)參數(shù),即當(dāng)前項(xiàng)的索引。語法格式為 (item, index) in items。
      <!DOCTYPE html>
      <html>
      	<head>
      		<meta charset="utf-8" />
      		<title></title>
      		<!--引入vue.js-->
      		<script src="lib/vue-2.6.12.js"></script>
      	</head>
      	<body>
      		<div id="app">
      			<!--遍歷數(shù)組-->
      			<p v-for="(score,index) in scores">{{index +':'+score}}</p>
      			
      			<!-- 遍歷對象數(shù)組 -->
      				<table border="1" align="center" width="300">
      					<thead style="background-color: orange;">
      						<tr align="center">
      							<td>姓名</td>
      							<td>年齡</td>
      							<td>性別</td>
      						</tr>
      					</thead>
      					<tbody>
      						<tr v-for="p in persons" align="center">
      							<td>{{p.name}}</td>
      							<td>{{p.age}}</td>
      							<td>{{p.sex}}</td>
      						</tr>
      					</tbody>
      			</table>
      			<!-- 對字符串進(jìn)行遍歷 -->
      			<p v-for ="str in hobby">
      				{{str}}
      			</p> 
      		</div>
      		
      		<script>
      			const vm = new Vue({
      				el: '#app',
      				data: {
      					scores: [100, 90, 80, 70],
      					persons: [
      						{ name: '張三', age: 23, sex: '男' },
      						{ name: '李四', age: 24, sex: '女' },
      						{ name: '王五', age: 25, sex: '男' },
      						{ name: '趙六', age: 26, sex: '女' },
      					],
      					hobby:'籃球'
      				}
      			});
      		</script>
      	</body>
      </html>
      測試結(jié)果:
      v-for指令使用
      使用 key 維護(hù)列表的狀態(tài)
      當(dāng)列表的數(shù)據(jù)變化時(shí),默認(rèn)情況下,vue 會盡可能的復(fù)用已存在的 DOM 元素,從而提升渲染的性能。但這種默認(rèn)的性能優(yōu)化策略,會導(dǎo)致有狀態(tài)的列表無法被正確更新。
      為了給 vue 一個(gè)提示,以便它能跟蹤每個(gè)節(jié)點(diǎn)的身份,從而在保證有狀態(tài)的列表被正確更新的前提下,提升渲染的性能。此時(shí),需要為每項(xiàng)提供一個(gè)唯一的 key 屬性:
      key 的注意事項(xiàng)
      ①key 的值只能是字符串或數(shù)字類型
      ②key 的值必須具有唯一性(即:key 的值不能重復(fù))
      ③建議把數(shù)據(jù)項(xiàng) id 屬性的值作為 key 的值(因?yàn)?id 屬性的值具有唯一性)
      ④使用 index 的值當(dāng)作 key 的值沒有任何意義(因?yàn)?index 的值不具有唯一性)
      ⑤建議使用 v-for 指令時(shí)一定要指定 key 的值(既提升性能、又防止列表狀態(tài)紊亂)

      二、過濾器

         過濾器(Filters)是 vue 為開發(fā)者提供的功能,常用于文本的格式化。過濾器可以用在兩個(gè)地方:插值表達(dá)式和 v-bind 屬性綁定。在創(chuàng)建 vue 實(shí)例期間,可以在 filters 節(jié)點(diǎn)中定義過濾 器。
         過濾器分為:私有過濾器(在filters節(jié)點(diǎn)下定義的過濾器,只能在當(dāng)前vm實(shí)例所控制的el區(qū)域內(nèi)使用)和全局過濾器(全局過濾器可以在多vue實(shí)例之間共享過濾器)。
      <!DOCTYPE html>
      <html>
      	<head>
      		<meta charset="utf-8" />
      		<title></title>
      		<!--引入vue.js-->
      		<script src="lib/vue-2.6.12.js"></script>
      	</head>
      	<body>
      		<div id="app">
      			<!-- 私有過濾器使用 -->
      			<p>{{sex | sexFormatter}}</p>
      			
      			<!-- 全局過濾器使用 -->
      			<p>{{str | capitalize}}</p>
      			
      			<!-- 連續(xù)調(diào)用多個(gè)過濾器 -->
      			<p>{{message | filterA | filterB}}</p>
      			
      			<!-- 過濾器傳參 -->
      			<p>{{message | maxLength(5)}}</p>
      		</div>
      		<script>
      			//全局過濾器 -獨(dú)立于每個(gè)vm實(shí)例之外,必須定義在vm實(shí)例之前
      			//Vue.filter()方法接受兩個(gè)參數(shù):
      			//第一個(gè)參數(shù),是全局過濾器的"名字"
      			//第二個(gè)參數(shù),是全局過濾器的"處理函數(shù)"
      			Vue.filter('capitalize',function(value){
      				return value.toUpperCase().split('').reverse().join('');
      			});
      			
      			//全局過濾器 - 控制文本的最大長度
      			Vue.filter('maxLength',function(str,len = 4){
      				if(str.length<=len) return str;
      				return str.slice(0,len)+'...';
      			});
      			
      			const vm = new Vue({
      				el:'#app',
      				data:{
      					sex:0,
      					str: 'abc',
      					message:'chensheng'
      				},
      				filters:{	//局部過濾器
      					sexFormatter(sex){
      						if(sex==0){
      							return "男";
      						}else{
      							return "女";
      						}
      					},
      					filterA(value){	//將首字母大寫
      						return value.charAt(0).toUpperCase()+value.slice(1);
      					},
      					filterB(value){	//將字符串反轉(zhuǎn)
      						return value.split('').reverse().join('');
      					}
      				}
      			});
      		</script>
      	</body>
      </html>
      測試結(jié)果:
      過濾器使用

      三、監(jiān)聽器

         如果我們需要監(jiān)聽某個(gè)值的變化,當(dāng)這個(gè)值變化是,進(jìn)行一些操作,可以使用監(jiān)聽器。監(jiān)聽器的屬性名稱是watch,和data平級。監(jiān)聽器中的數(shù)據(jù)是方法,接收兩個(gè)參數(shù),分別為改變后的值和改變前的值。如果想讓wath偵聽器立即被調(diào)用,則需要使用immediate選項(xiàng)。
      <!DOCTYPE html>
      <html>
      	<head>
      		<meta charset="utf-8" />
      		<title></title>
      		<!--引入vue.js-->
      		<script src="lib/vue-2.6.12.js"></script>
      	</head>
      	<body>
      		<div id="app">
      			firstName:<input type="text" v-model="firstName" />
      			lastName:<input type="text" v-model="lastName" />
      			<h2>{{fullName}}</h2>
      			person:<input type="text" v-model="person.username" />
      		</div>
      		
      		<script>
      			const vm = new Vue({
      				el:'#app',
      				data:{
      					firstName:'',
      					lastName:'',
      					fullName:'',
      					person:{username:'admin'}
      				},
      				watch:{
      					firstName(newVal,oldVal){
      						//在vue中,操作data、method必須使用this
      						this.fullName = this.firstName + this.lastName;
      					},
      					lastName(newVal,oldVal){
      						this.fullName = this.firstName + this.lastName;
      					},
      					person:{             //監(jiān)聽對象內(nèi)屬性變化,handler是固定寫法,當(dāng)username值變化時(shí),自動調(diào)用handler處理函數(shù)
      						handler(newVal){
      							console.info('如果監(jiān)聽對象內(nèi)屬性變化,則使用這種方式'+newVal.username);
      						},
      					    deep: true,		 //如果watch偵聽的是一個(gè)對象,如果對象中的屬性值發(fā)生了變化,則無法被監(jiān)聽到,需要使用deep選項(xiàng)才能偵聽
      						immediate:true   //表示頁面初次渲染好之后,就立即觸發(fā)當(dāng)前的watch偵聽器
      					},
      					'person.username':{
      						handler(newVal){
      							console.info('如果只想監(jiān)聽對象單個(gè)屬性變化,則使用這種方式'+newVal)
      						}
      					}
      				}
      			});
      		</script>
      	</body>
      </html>
      測試結(jié)果:

      watch監(jiān)聽器使用

      四、計(jì)算屬性

      計(jì)算屬性指的是通過一系列運(yùn)算之后,最終得到一個(gè)屬性值。這個(gè)動態(tài)計(jì)算出來的屬性值可以被模板結(jié)構(gòu)或 methods 方法使用。
      <!DOCTYPE html>
      <html>
      	<head>
      		<meta charset="utf-8" />
      		<title></title>
      		<!--引入vue.js-->
      		<script src="lib/vue-2.6.12.js"></script>
      	</head>
      	<body>
      		<div id="app">
      			<p @click='show()'>計(jì)算屬性: {{reverseMsg}}</p>
      		</div>
      		
      		<script>
      			const vm = new Vue({
      				el:'#app',
      				data:{
      				   msg: 'hello world'
      				},
      				computed: {
      					//計(jì)算屬性的getter
      					reverseMsg: function() {
      						//this指向vm實(shí)例
      						return this.msg.split('').reverse().join('');
      					}
      				},
      				methods:{
      					show(){
      						console.info(this.reverseMsg);  //在methods中調(diào)用屬性
      					}
      				}
      			});
      		</script>
      	</body>
      </html>
      測試結(jié)果:
      計(jì)算屬性使用

      計(jì)算屬性和method區(qū)別?

      •    當(dāng)頁面重新渲染(不是刷新)的時(shí)候,計(jì)算屬性不會變化,直接讀取緩存使用,適合較大量的計(jì)算和改變頻率較低的屬性;而method就是當(dāng)頁面重新渲染的時(shí)候(頁面元素的data變化,頁面就會重新渲染),都會重新調(diào)用method。
      •    計(jì)算屬性是一個(gè)屬性,而不是方法。雖然寫法是方法,但是我們使用的時(shí)候是直接視為一個(gè)屬性去操作的,使用方式和data一致。
      •    計(jì)算屬性中使用到的data中的數(shù)據(jù)只要發(fā)生了變化,計(jì)算屬性就會重新計(jì)算。如果兩次獲取計(jì)算屬性的時(shí)候,里面使用到的屬性沒有發(fā)生變化,計(jì)算屬性會直接使用之前緩存的值。

      注意點(diǎn):

      •    計(jì)算屬性。在computed中,可以定義一些屬性,這些屬性叫做計(jì)算屬性,他本質(zhì)上就是一個(gè)方法,但是,我們使用的時(shí)候是當(dāng)做屬性來使用。計(jì)算屬性使用的過程中,一定不要加(),它就是一個(gè)屬性,和data里的屬性用法一樣。
      •    只要極速暗屬性中所用到的data中的屬性發(fā)生了變化,就會立即去重新計(jì)算屬性的值。
      •    計(jì)算屬性的結(jié)果會被緩存起來,方便下次調(diào)用,如果計(jì)算屬性中用到的data都沒有變化,就不會重新求值。
      •   在計(jì)算屬性中,無論如何都需要return一個(gè)值,用來代表這個(gè)屬性的值。

      計(jì)算屬性和監(jiān)聽器的區(qū)別:

      • Computed用法視為一個(gè)屬性,并且結(jié)果會被緩存。
      • Methods表示方法,表示一個(gè)具體的操作,主要用來寫業(yè)務(wù)邏輯
      • Watch是一個(gè)對象,key是需要監(jiān)聽的表達(dá)式,value是對應(yīng)的回調(diào)函數(shù),主要用來監(jiān)聽某些數(shù)據(jù)的變化,從而執(zhí)行某些具體的業(yè)務(wù)邏輯。可以看做是計(jì)算屬性和methods的結(jié)合體。

      五、全局組件

      組件是可復(fù)用的Vue實(shí)例,且?guī)б粋€(gè)名字,可以復(fù)用。我們搭建的頁面其實(shí)是一個(gè)個(gè)組件組裝而成,可以分為局部組件和全局組件。

      • 局部組件:只屬于當(dāng)前Vue的實(shí)例,其他實(shí)例無法共享這個(gè)局部組件。

      <!DOCTYPE html>
      <html>
      	<head>
      		<meta charset="utf-8" />
      		<title></title>
      		<!--引入vue.js-->
      		<script src="lib/vue-2.6.12.js"></script>
      	</head>
      	<body>
      		<div id="app">
      			<my-date></my-date>
      		</div>
      		
      		<script>
      			//1、創(chuàng)建組件構(gòu)造器
      			let partialTemplate = Vue.extend({
      				template:`
      							<div>
      								<input type='date'/>
      								<p>今天天氣好晴朗!</p>
      							</div>
      						`
      			});
      			const vm = new Vue({
      				el: '#app',
      				// 注冊局部組件,只屬于當(dāng)前的vue實(shí)例
      				components:{
      					'my-date':partialTemplate
      				}
      			});
      		</script>
      	</body>
      </html>
      
      局部組件簡潔寫法:
      			const vm = new Vue({
      				el: '#app',
      				// 注冊局部組件,只屬于當(dāng)前的vue實(shí)例
      				components:{
      					'my-date':{
      						template:`
      							<div>
      								<input type='date'/>
      								<p>今天天氣好晴朗!</p>
      							</div>
      							`
      					}
      				}
      			});

      測試結(jié)果:

      vue注冊局部組件

      • 全局組件:屬于所有的Vue實(shí)例所有。

      <!DOCTYPE html>
      <html>
      	<head>
      		<meta charset="utf-8" />
      		<title></title>
      		<!--引入vue.js-->
      		<script src="lib/vue-2.6.12.js"></script>
      	</head>
      	<body>
      		<div id="app">
      			<my-date></my-date>
      		</div>
      		
      		<script>
      			//1. 創(chuàng)建組件構(gòu)造器
      			let ProFile = Vue.extend({
      				//1.1 模板選項(xiàng)
      				template:`
      					<div>
      						<input type="date"/>
      						<p>今天天氣好晴朗!</p>
      					</div>
      				`
      			});
      
      			//2. 注冊全局組件,參數(shù)1自定義組件名稱,參數(shù)2組件
      			Vue.component('my-date',ProFile);
      			
      			const vm = new Vue({
      				el: '#app'
      			});
      		</script>
      	</body>
      </html>
      測試結(jié)果同上!

      六、父子組件

      <!DOCTYPE html>
      <html>
      	<head>
      		<meta charset="utf-8" />
      		<title></title>
      		<!--引入vue.js-->
      		<script src="lib/vue-2.6.12.js"></script>
      	</head>
      	<body>
      		<div id="app">
      			<parent></parent>
      		</div>
      		<script>
      			// 1. 子組件構(gòu)造器
      			let Child1 = Vue.extend({
      				template: `<img src="img/estar.ico" width="200">`
      			});
      
      			let Child2 = Vue.extend({
      				template: `<p>孤獨(dú)的星星!</p>`
      			});
      
      			// 2. 父組件構(gòu)造器
      			Vue.component('parent', {
      				components: { 			  //注冊子組件
      					'my-child1': Child1,
      					'my-child2': Child2
      				},
      				template: `               //組裝父組件
                        <div>
                            <my-child1></my-child1>
                            <my-child2></my-child2>
                        </div>
                      `
      			});
      
      			new Vue({
      				el: '#app'
      			});
      		</script>
      	</body>
      </html>
      測試結(jié)果:
      父子組件
      • template標(biāo)簽和script標(biāo)簽注冊組件
      	一、使用template來注冊組件【常用】
                      <body>
                          <div id="app">
                              <!-- 使用父組件 -->
                              <my-div></my-div>
                          </div>
                          <template id="parent">
                              <!-- 只能有一個(gè)出口,最外層必須有標(biāo)簽包裹 -->
                              <div>
                                  <img src="img/estar.ico" width="200">
                                  <p>孤獨(dú)的星星!</p>
                              </div>
                          </template>
                          <script>
                              //實(shí)例化組件
                              Vue.component('my-div', {
                                  template: '#parent'
                              });
      
                              new Vue({
                                  el: '#app'
                              });
                          </script>
                      </body>
       	二、使用script來注冊組件,必須聲明類型type=”text/template” 【不推薦使用】
                      <body>
                          <div id="app">
                              <!-- 使用父組件 -->
                              <my-div></my-div>
                          </div>
                          <script type="text/template" id="parent">
                              <!-- 只能有一個(gè)出口,最外層必須有標(biāo)簽包裹 -->
                              <div>
                                  <img src="img/estar.ico" width="200">
                                  <p>孤獨(dú)的星星!</p>
                              </div>
                          </script>
                          <script>
                              //實(shí)例化組件
                              Vue.component('my-div', {
                                  template: '#parent'
                              });
      
                              new Vue({
                                  el: '#app'
                              });
                          </script>
                  	</body>
      • 組件中data使用
      下述在組件中直接調(diào)用data中的數(shù)據(jù)會報(bào)錯(cuò),如下所示:
       為什么組件的data必須是一個(gè)方法?
        首先,如果不是一個(gè)方法,Vue直接會報(bào)錯(cuò)。其次,原因在于Vue讓每一個(gè)組件對象都返回一個(gè)新的對象,如果是同一個(gè)對象的,組件會在多次使用后相互影響。如果我們不寫成方法返回對象的話,那么就是所有組件公用一個(gè)data。

      u  我們將data定義成函數(shù),這樣每個(gè)按鈕點(diǎn)擊后都會產(chǎn)生自己獨(dú)享的變量,而不是共享的變量。

      <!DOCTYPE html>
      <html>
      	<head>
      		<meta charset="utf-8" />
      		<title></title>
      		<!--引入vue.js-->
      		<script src="lib/vue-2.6.12.js"></script>
      	</head>
      
      	<body>
      		<div id="app">
      			<!-- 使用組件 -->
      			<my-btn></my-btn>
      			<my-btn></my-btn>
      			<my-btn></my-btn>
      		</div>
      		<template id="btn_group">
      			<button @click="counter++">按鈕點(diǎn)擊次數(shù){{counter}}</button>
      		</template>
      		<script>
      			//實(shí)例化組件
      			Vue.component('my-btn', {
      				template: '#btn_group',
      				data() {
      					return { counter: 0 }
      				}
      			});
      
      			new Vue({
      				el: '#app'
      
      			});
      		</script>
      	</body>
        </html>

      測試結(jié)果:(描述,我們點(diǎn)擊不同的按鈕統(tǒng)計(jì)的counter都是自己的)

      u  如果我們將counter定義到外面來

      <!DOCTYPE html>
      <html>
      
      	<head>
      		<meta charset="utf-8" />
      		<title></title>
      		<!--引入vue.js-->
      		<script src="lib/vue-2.6.12.js"></script>
      	</head>
      
      	<body>
      		<div id="app">
      			<!-- 使用組件 -->
      			<my-btn></my-btn>
      			<my-btn></my-btn>
      			<my-btn></my-btn>
      		</div>
      		<template id="btn_group">
      			<button @click="counter++">按鈕點(diǎn)擊次數(shù){{counter}}</button>
      		</template>
      
      		<script>
      			//組件將共享一個(gè)countDate
      			let countDate = { counter: 0 };
      			Vue.component('my-btn', {
      				template: '#btn_group',
      				data() {
      					return countDate;
      				}
      			});
      
      			new Vue({
      				el: '#app'
      			});
      		</script>
      	</body>
       </html>

      測試結(jié)果:(描述:我們點(diǎn)擊其中一個(gè)按鈕其他按鈕點(diǎn)擊次數(shù)也會隨之改變,共享一個(gè)counter值)


      七、組件通信

       父子組件之間的通信,父組件通過 prop 給子組件下發(fā)數(shù)據(jù),子組件通過$emit觸發(fā)事件給父組件發(fā)送消息,即 prop 向下傳遞,事件向上傳遞。

      • 父組件向子組件傳值(簡單的單層組件之間的值傳遞)

           首先在父組件中使用v-bind將數(shù)組綁定給子組件,再在子組件中,使用props收。

         <body>
                  <div id="app">
                      <my-div :msg='孤獨(dú)的星星' imgsrc='img/estar.ico'></my-div>
                  </div>
                  <template id="my_div">
                      <div>
                          <h1>{{msg}}</h1>
                          <img :src="imgsrc" width="100" height="100" />
                      </div>
                  </template>
      
                  <script>
                      //實(shí)例化組件
                      Vue.component('my-div', {
                          template: '#my_div',
                          props:['msg','imgsrc'] //父組件通過props向子組件傳遞值
                      });
      
                      new Vue({
                          el: '#app'
                      });
                  </script>
              </body>
         
         或者使用綁定的方式將父組件的值傳遞給子組件:
          <body>
                  <div id="app">
                  	<!-- 使用綁定的方式,將父組件的數(shù)據(jù)綁定給子組件 -->
                      <my-div :msg='msg' :imgsrc='imgsrc'></my-div>
                  </div>
                  
                  <template id="my_div">
                      <div>
                          <h1>{{msg}}</h1>
                          <img :src="imgsrc" width="100" height="100" />
                      </div>
                  </template>
      
                  <script>
                      //實(shí)例化組件
                     const myCom =  Vue.component('my-div', {
      				                    template: '#my_div',
      				                    props:['msg','imgsrc'] //父組件通過props向子組件傳遞值,或者寫法如下
                                         //props: {
                                         //  msg: {
                                         //   type: String,   //type支持的類型有: String、Number、Boolean、Array、Object、Date、Function、Symbol
                                         //   default: '我是默認(rèn)值,父組件沒有傳給我msg'
                                         // }
                                         // }
      				                });
      
                      new Vue({
                          el: '#app',
                          data:{
                          	msg:'孤獨(dú)的星星',
                          	imgsrc:'img/estar.ico'
                          },
                          components:{
                          	myCom
                          }
                      });
                  </script>
              </body>

      測試結(jié)果:
      父組件向子組件傳值之單層組件傳值
      • 父組件向子組件傳值(多層組件之間的值傳遞)

      多層組件傳值示意圖

      <!DOCTYPE html>
      <html>
      	<head>
      		<meta charset="utf-8" />
      		<title></title>
      		<!--引入vue.js-->
      		<script src="lib/vue-2.6.12.js"></script>
      	</head>
      
      	<body>
      		<div id="app">
      			<!-- 使用父組件 -->
      			<my-parent :imgtitle="title" :imgsrc="img"></my-parent>
      		</div>
      		<!-- 定義子組件 -->
      		<template id="my_img">
      			<img :src="imgsrc" width="200" />
      		</template>
      		<template id="my_title">
      			<h2>{{title}}</h2>
      		</template>
      		<!-- 定義父組件 -->
      		<template id="my_parent">
      			<div>
      				<child1 :imgsrc="imgsrc"></child1>
      				<child2 :title="imgtitle"></child2>
      			</div>
      		</template>
      
      		<script>
      			//1.子組件的實(shí)例
      			let child1 = Vue.extend({
      				template: '#my_img',
      				props: ['imgsrc']
      			});
      			let child2 = Vue.extend({
      				template: '#my_title',
      				props: ['title']
      			});
      			//2.注冊父組件
      			Vue.component('my-parent', {
      				props: ['imgtitle', 'imgsrc'],
      				components: {
      					'child1': child1,
      					'child2': child2
      				},
      				template: '#my_parent'
      			});
      
      			new Vue({
      				el: '#app',
      				data: {
      					title: '孤獨(dú)的星星',
      					img: 'img/estar.ico'
      				}
      			});
      		</script>
      	</body>
       </html>

      測試結(jié)果:
      父組件向子組件傳值之多層組件傳值

      • 父組件向子組件傳遞事件

         我們知道父組件是使用props傳遞數(shù)據(jù)給子組件,但如果子組件要把數(shù)據(jù)傳遞回去,則應(yīng)該使用自定義事件來完成!

       使用$on(eventName)監(jiān)聽事件,使用$emit(eventName)來觸發(fā)事件,另外父組件可以在使用子組件的地方直接使用v-on來監(jiān)聽子組件除法的事件。

      描述: 我們在父組件中自定義一個(gè)total事件,當(dāng)我們觸發(fā)這個(gè)total()事件的時(shí)候通過$emit('total')來觸發(fā)外界定義的@total="allcounter()"中
            的具體的方法allcounter()。注意在此案例中按鈕與按鈕之間是相互獨(dú)立的,互不影響。
      <!DOCTYPE html>
      <html>
      	<head>
      		<meta charset="utf-8" />
      		<title></title>
      		<!--引入vue.js-->
      		<script src="lib/vue-2.6.12.js"></script>
      	</head>
      
      	<body>
      		<div id="app">
      			<!—自定義事件-->
      			<my-btn @total="allcounter()"></my-btn>
      			<my-btn @total="allcounter()"></my-btn>
      			<my-btn @total="allcounter()"></my-btn>
      			<my-btn @total="allcounter()"></my-btn>
      			<p>所有按鈕一共點(diǎn)擊了{(lán){totalCounter}}次</p>
      		</div>
      		<template id="my_btn">
      			<button @click="total()">點(diǎn)擊了{(lán){counter}}次</button>
      		</template>
      		<script>
      			Vue.component('my-btn', {
      				template: '#my_btn',
      				data() {
      					return {
      						counter: 0
      					}
      				},
      				methods: {
      					total() {
      						this.counter += 1; //不同的按鈕享有不同的counter
      						// 通知外界,我調(diào)用了這個(gè)方法
      						this.$emit('total');
      					}
      				}
      			});
      
      			new Vue({
      				el: '#app',
      				data: {
      					totalCounter: 0 //公共的數(shù)據(jù)
      				},
      				methods: {
      					allcounter() {
      						this.totalCounter += 1;
      					}
      				}
      			});
      		</script>
      	</body>
       </html>

      測試結(jié)果:(描述我們低級不同的按鈕分別統(tǒng)計(jì)不同的按鈕點(diǎn)擊次數(shù),互不影響)

      父組件向子組件傳遞事件

      • 父組件調(diào)用子組件方法

        $refs是和ref一起使用的。通過ref給某個(gè)子組件綁定一個(gè)特定的ID,然后我們使用$refs.ID就可以訪問到子組件了。

      <!DOCTYPE html>
      <html>
      
      	<head>
      		<meta charset="utf-8" />
      		<title></title>
      		<!--引入vue.js-->
      		<script src="lib/vue-2.6.12.js"></script>
      
      	</head>
      
      	<body>
      		<div id="app">
      			<button @click="countAdd">點(diǎn)我</button>
      			<!-- 第一步,給子組件綁定一個(gè)ref -->
      			<my-com ref="myComp"></my-com>
      		</div>
      
      		<template id="myTemp">
      			<div>
      				{{count}}
      			</div>
      		</template>
      		<script>
      			let myCom = Vue.extend({
      				template: '#myTemp',
      				data() {
      					return {
      						count: 1
      					}
      				},
      				methods: {
      					addCount() {
      						this.count++
      					}
      				}
      			})
      			let app = new Vue({
      				el: '#app',
      				methods: {
      					countAdd() {
      						// 第二步,在父組件中使用this.$refs.id就行了
      						console.log(this.$refs.myComp.count)
      						this.$refs.myComp.addCount()
      					}
      				},
      				components: {
      					myCom
      				}
      			})
      		</script>
      	</body>
      </html>
      測試結(jié)果:
      父組件調(diào)用子組件方法

      八、插槽

        Slot插槽實(shí)現(xiàn)內(nèi)容分發(fā),結(jié)合日常生活中的電路板,有指定插孔,我們可以插入任何電器插頭(匿名插槽),也有專門針對手機(jī)的USB插頭(實(shí)名插槽),無法插入其他電器插頭。

      • 匿名插槽

      	<body>
      		<div id="app">
      			<my-slot>
      				<img src="img/estar.ico" width="200" alt="">
      				<p>{{msg}}</p>
      			</my-slot>
      		</div>
      		<template id="my_slot">
      			<div>
      				<header>插槽的頭部</header>
      				<!--預(yù)留一個(gè)插槽,沒有則顯示該插槽內(nèi)容-->
      				<slot>可以替換任何標(biāo)簽,默認(rèn)顯示提示的內(nèi)容</slot>
      				<footer>插槽的尾部</footer>
      			</div>
      		</template>
      		<script>
      			Vue.component('my-slot', {
      				template: '#my_slot'
      			});
      
      			new Vue({
      				el: '#app',
      				data: {
      					msg: '孤獨(dú)的星星'
      				}
      			});
      		</script>
      	</body>

      測試結(jié)果:
      匿名插槽

      • 實(shí)名插槽

      <body>
      		<div id="app">
      			<my-computer>
      				<div slot="cpu">core-i7 6700HQ處理器</div>
      				<div slot="memory">Kingston-32G內(nèi)存條</div>
      			</my-computer>
      		</div>
      
      		<template id="my_computer">
      			<div>
      				<slot name="cpu">默認(rèn)插cpu的</slot>
      				<slot name="memory">默認(rèn)插內(nèi)存條的</slot>
      				<slot name="hard-drive">默認(rèn)插硬盤的</slot>
      			</div>
      		</template>
      		<script>
      			Vue.component('my-computer', {
      				template: '#my_computer'
      			});
      
      			new Vue({
      				el: '#app'
      			});
      		</script>

      測試結(jié)果:
      實(shí)名插槽

      九、路由

                        https://www.jianshu.com/p/2acf9e23793a
      前端路由和后端路由:
      • 后端路由:對于普通的網(wǎng)站,所有的超鏈接都是url地址,所有url都對應(yīng)服務(wù)器上對應(yīng)的資源
      • 前端路由:對于單頁面應(yīng)用程序來說,主要通過url的hash(#)來實(shí)現(xiàn)不同頁面的切換,同時(shí)hash還有一個(gè)特點(diǎn)HTTP請求中不會包含hash相關(guān)的內(nèi)容,所以單頁面程序中的頁面跳轉(zhuǎn)主要用hash實(shí)現(xiàn)
        在單頁面應(yīng)用程序中這種通過hash來改變頁面的方式稱作前端路由區(qū)別于后端路由
      ==>由于Vue在開發(fā)時(shí)對路由支持的不足,于是官方補(bǔ)充了vue-router插件。vue的單頁面應(yīng)用是基于路由和組件的,路由用于設(shè)定訪問路徑,并將路徑和組件映射起來。
      • 引入vue-router
            <script src="lib/vue-router.js"></script>  

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

      • 路由入門

          創(chuàng)建一個(gè)路由對象,當(dāng)導(dǎo)入vue-router包之后,在window全局對象中就有一個(gè)路由的構(gòu)造函數(shù)VueRouter
      在new路由對象的時(shí)候可以傳遞一個(gè)配置對象,這個(gè)配置對象的route表示路由器的匹配規(guī)則
      每個(gè)路由規(guī)則都是一個(gè)對象,這個(gè)規(guī)則對象身上必須有兩個(gè)屬性
      屬性1 path表示監(jiān)聽哪個(gè)路由鏈接地址
      屬性2 component,表示如果路由是前面匹配到的path,則展示component屬性對應(yīng)的組件,component屬性值必須是一個(gè)組件模板對象,不能是組件的引用名稱

      <!DOCTYPE html>
      <html>
      	<head>
      		<meta charset="utf-8" />
      		<title></title>
      		<script src="lib/vue-2.6.12.js"></script>
      		<script src="lib/vue-router.js"></script>
      		<style>
      			ul li {
      				float: left;
      				width: 300px;
      				height: 70px;
      				box-sizing: border-box;
      				background-color: pink;
      				list-style: none;
      				line-height: 70px;
      				text-align: center;
      			}
      			
      			ul li a {
      				text-decoration: none;
      				font-size: 20px;
      			}
      			
      			.content {
      				clear: both;
      				width: 900px;
      				box-sizing: border-box;
      				border: 1px solid blue;
      				padding-left: 20px;
      				margin-left: 40px;
      			}
      		</style>
      	</head>
      		<body>
      			<div id="app">
      				<!-- 使用 router-link 組件來導(dǎo)航. -->
      				<!-- 通過傳入 `to` 屬性指定鏈接. -->
      				<!-- <router-link> 默認(rèn)會被渲染成一個(gè) `<a>` 標(biāo)簽 -->
      				<ul>
      					<li>
      						<router-link to="/h5">HTML5學(xué)院</router-link>
      					</li>
      					<li>
      						<router-link to="/python">Python學(xué)院</router-link>
      					</li>
      					<li>
      						<router-link to="/java">Java學(xué)院</router-link>
      					</li>
      				</ul>
      				<div class="content">
      					<!-- 路由出口 -->
      					<!-- 路由匹配到的組件將渲染在這里 -->
      					<router-view></router-view>
      				</div>
      			</div>
      
      			<template id="h5">
      				<div>
      					<h2>HTML5學(xué)院</h2>
      					<p>掌握面向未來的神技!</p>
      				</div>
      			</template>
      			<template id="python">
      				<div>
      					<h2>Python學(xué)院</h2>
      					<p>人工智能的最佳選擇!</p>
      				</div>
      			</template>
      			<template id="java">
      				<div>
      					<h2>Java學(xué)院</h2>
      					<p>掌握面向工資編程!</p>
      				</div>
      			</template>
      			<script>
      				//1.創(chuàng)建組件
      				const Html5 = Vue.extend({
      					template: '#h5'
      				});
      				const Python = Vue.extend({
      					template: '#python'
      				});
      				const Java = Vue.extend({
      					template: '#java'
      				});
      				//2.定義路由
      				const routes = [
      					{ path: '/h5', component: Html5 },
      					{ path: '/python', component: Python },
      					{ path: '/java', component: Java },
      					//配置根路由,默認(rèn)顯示
      					{ path: '/', redirect: '/h5' }
      				];
      				//3.創(chuàng)建路由實(shí)例
      				const router = new VueRouter({
      					routes
      				});
      				//4.創(chuàng)建Vue實(shí)例并掛載
      				new Vue({
      					router
      				}).$mount('#app');
      			</script>
      		</body>
      	</body>
      </html>

      測試結(jié)果: (描述:我們點(diǎn)擊不同的tab切換頁能實(shí)現(xiàn)展示不同的內(nèi)容)

      vue路由使用
      補(bǔ)充:上述代碼存在一個(gè)弊端,就是<router-link to="/h5">HTML5學(xué)院</router-link>路由時(shí)我們需要將路由路徑寫死在頁面上,建議采用動態(tài)綁定的方式會更好。下面采用給路由命名的方式來解決這個(gè)問題

      <body>
      		<div id="app">
      			<!-- 使用 router-link 組件來導(dǎo)航. -->
      			<!-- 通過傳入 `to` 屬性指定鏈接. -->
      			<!-- <router-link> 默認(rèn)會被渲染成一個(gè) `<a>` 標(biāo)簽 -->
      			<ul>
      				<li><router-link :to="{name:'h5'}">HTML5學(xué)院</router-link></li>
      				<li><router-link :to="{name:'python'}">Python學(xué)院</router-link></li>
      				<li><router-link :to="{name:'java'}">Java學(xué)院</router-link></li>
      			</ul>
      			<div class="content">
      				<!-- 路由出口 -->
                      <!-- 路由匹配到的組件將渲染在這里 -->
                      <router-view></router-view>
      			</div>
      		</div>
      
      		<template id="h5">
      			<div>
      				<h2>HTML5學(xué)院</h2>
      				<p>掌握面向未來的神技!</p>
      			</div>
      		</template>
      		<template id="python">
      			<div>
      				<h2>Python學(xué)院</h2>
      				<p>人工智能的最佳選擇!</p>
      			</div>
      		</template>
      		<template id="java">
      			<div>
      				<h2>Java學(xué)院</h2>
      				<p>掌握面向工資編程!</p>
      			</div>
      		</template>
      		<script>
      			//1.創(chuàng)建組件
      			const Html5 = Vue.extend({
      				template: '#h5'
      			});
      			const Python = Vue.extend({
      				template: '#python'
      			});
      			const Java = Vue.extend({
      				template: '#java'
      			});
      			//2.定義路由
      			const routes = [
      				{ path: '/h5', component: Html5,name:'h5' },
      				{ path: '/python', component: Python,name:'python' },
      				{ path: '/java', component: Java ,name:'java'},
      				//配置根路由,默認(rèn)顯示
      				{ path: '/', redirect: '/h5' }
      			];
      			//3.創(chuàng)建路由實(shí)例
      			const router = new VueRouter({
      				routes
      			});
      			//4.創(chuàng)建Vue實(shí)例并掛載
      			new Vue({
      				router
      			}).$mount('#app');
      		</script>
      	</body>

      • 多級子路由

        	<body>
        		<div id="app">
        			<!-- 使用 router-link 組件來導(dǎo)航. -->
        			<!-- 通過傳入 `to` 屬性指定鏈接. -->
        			<!-- <router-link> 默認(rèn)會被渲染成一個(gè) `<a>` 標(biāo)簽 -->
        			<ul>
        				<li><router-link to="/h5">HTML5學(xué)院</router-link></li>
        				<li><router-link to="/python">Python學(xué)院</router-link></li>
        				<li><router-link to="/java">Java學(xué)院</router-link></li>
        			</ul>
        			<div class="content">
        				<!-- 路由出口 -->
                        <!-- 路由匹配到的組件將渲染在這里 -->
                        <router-view></router-view>
        			</div>
        		</div>
        
        		<template id="h5">
        			<div>
        				<h2>HTML5學(xué)院</h2>
        				<p>掌握面向未來的神技!</p>
        			</div>
        		</template>
        		<template id="python">
        			<div>
        				<h2>Python學(xué)院</h2>
        				<p>人工智能的最佳選擇!</p>
        			</div>
        		</template>
        		<template id="java">
        			<div>
        				<h2>Java學(xué)院</h2>
        				<p>掌握面向工資編程!</p>
        				<!--子組件路由-->
        				<router-link  to="/java/base">基礎(chǔ)班</router-link>
                        <router-link  to="/java/advance">進(jìn)階班</router-link>
        				<div>
        					<!-- 子組件出口 -->
                            <router-view></router-view>
                        </div>
        			</div>
        		</template>
        		<!-- 定義Java組件下的子組件 -->
        		<template id="base">
        	        <div>
        	            <h3>Java基礎(chǔ)班</h3>
        	            <p>快速掌握J(rèn)ava的三大特性!</p>
        	        </div>
        	    </template>
        
        	    <template id="advance">
        	        <div>
        	            <h3>Java進(jìn)階班</h3>
        	            <p>掌握高并發(fā)高可用的架構(gòu)!</p>
        	        </div>
        	    </template>
        		<script>
        			//1.創(chuàng)建組件
        			const Html5 = Vue.extend({
        				template: '#h5'
        			});
        			const Python = Vue.extend({
        				template: '#python'
        			});
        			const Java = Vue.extend({
        				template: '#java'
        			});		
        			//創(chuàng)建Java的子組件
        			const base = Vue.extend({
        				template: '#base'
        			});	
        			const advance = Vue.extend({
        				template: '#advance'
        			});	
        			
        			//2.定義路由
        			const routes = [
        				{ path: '/h5', component: Html5 },
        				{ path: '/python', component: Python },
        				{ path: '/java', component: Java,
        				children: [  //使用children屬性實(shí)現(xiàn)路由嵌套,子路由path前不要加/,否則永遠(yuǎn)以根路徑開始請求
                            {path:'base', component: base},
                            {path:'advance', component: advance},
                            // 配置Java組件的根路由,默認(rèn)顯示
                            {path:'/', redirect: 'base'}
                        ]
        				},
        				//配置根路由,默認(rèn)顯示
        				{ path: '/', redirect: '/h5' }
        			];
        			//3.創(chuàng)建路由實(shí)例
        			const router = new VueRouter({
        				routes
        			});
        			//4.創(chuàng)建Vue實(shí)例并掛載
        			new Vue({
        				router
        			}).$mount('#app');
        		</script>
        	</body>

      測試結(jié)果:

      vue多級子路由使用

      • 路由傳參

      1. 如果使用查詢字符串 給路由傳遞參數(shù)則不需要修改路由規(guī)則的path屬性,直接在組件當(dāng)中使用{$route.query.字段名}}即可獲取值。
      <!DOCTYPE html>
      <html>
      	<head>
      		<meta charset="utf-8" />
      		<title></title>
      		<script src="lib/vue-2.6.12.js"></script>
      		<script src="lib/vue-router.js"></script>
      	</head>
      	<body>
      		<div id="app">
      			<!-- 路由入口 -->
      			<router-link to="/login?username=zs&password=123">登錄</router-link>
      
      			<div>
      				<!-- 路由出口 -->
      				<router-view></router-view>
      			</div>
      		</div>
              
      		<template id="userInfo">
      			<div>
      				用戶:{{$route.query.username}},密碼:{{$route.query.password}}
      			</div>
      		</template>
      		<script>
      			//1.創(chuàng)建組件
      			const userInfo = Vue.extend({
      				template: '#userInfo'
      			});
      
      			//2.定義路由
      			const routes = [
      				{ path: '/login', component: userInfo },
      				//配置根路由,默認(rèn)顯示
      				{ path: '/', redirect: 'login' }
      			];
      			//3.創(chuàng)建路由實(shí)例
      			const router = new VueRouter({
      				routes
      			});
      			//4.創(chuàng)建Vue實(shí)例并掛載
      			new Vue({
      				router
      			}).$mount('#app');
      		</script>
      	</body>
      </html>
      測試結(jié)果:
      2. 通過params方式傳遞路由參數(shù),login后面會被解析為id的值
          <router-link to="/login/zs">登錄</router-link>
      
          { path: '/login/:username', component: userInfo }
      
          <template id="userInfo">
              <div>
                  用戶:{{$route.params.username}}
              </div>
          </template>
      

      測試結(jié)果:

      十、過渡動畫

      Vue中為我們提供了簡單的過渡動畫效果,只需要按照vue提供的標(biāo)準(zhǔn)去寫一套固定的CSS即可。

        <style>
          /* v-enter 這個(gè)是一個(gè)時(shí)間點(diǎn),表示動畫進(jìn)入之前,元素的起始狀態(tài),此時(shí)還沒有進(jìn)入 */
          /* v-leave-to 這是一個(gè)時(shí)間點(diǎn),是動畫離開之后,元素的終止?fàn)顟B(tài),此時(shí),元素動畫已經(jīng)結(jié)束了 */
          .v-enter,
          .v-leave-to {
            opacity: 0;
            transform: translateX(50px);
          }
          
          /* v-enter-active 表示入場動畫的時(shí)間段 */
          /* v-leave-active 表示離場動畫的時(shí)間段 */
          .v-enter-active,
          .v-leave-active {
            transition: all 0.8s ease;
          }
        </style>
      
      <body>
        <div id="app">
          <button @click="flag = !flag">點(diǎn)擊</button>
          <transition>
            <div v-show="flag">這個(gè)是第一個(gè)div</div>
          </transition>
        </div>
      </body>
      <script>
        let app = new Vue({
          el: '#app',
          data: {
            flag: true
          },
          methods: {
          }
        })
      </script>
      測試結(jié)果:
      此時(shí)如果我們想要讓div1消失后,div2進(jìn)來,div2消失后div1進(jìn)來,應(yīng)該怎么辦?只需要寫兩套動畫即可
          <transition>
            <div v-show="flag">這個(gè)是第一個(gè)div</div>
          </transition>
          <transition>
            <div v-show="!flag">這個(gè)是第二個(gè)div</div>
          </transition>

      如果div1和div2不想公用一套動畫,應(yīng)該怎么辦?這時(shí)候我們可以給transition命名,使用name屬性即可。定義了name之后,兩個(gè)transition則使用自己獨(dú)立的動畫效果。定義了name之后,動畫的相關(guān)class,要以name開頭,不能以v開頭。

          <transition name="div1">
            <div v-show="flag">這個(gè)是第一個(gè)div</div>
          </transition>
          <transition name="div2">
            <div v-show="!flag">這個(gè)是第二個(gè)div</div>
          </transition>
        <style>
          /* v-enter 這個(gè)是一個(gè)時(shí)間點(diǎn),表示動畫進(jìn)入之前,元素的起始狀態(tài),此時(shí)還沒有進(jìn)入 */
          /* v-leave-to 這是一個(gè)時(shí)間點(diǎn),是動畫離開之后,元素的終止?fàn)顟B(tài),此時(shí),元素動畫已經(jīng)結(jié)束了 */
          .div1-enter,
          .div1-leave-to {
            opacity: 0;
            transform: translateX(50px);
          }
          
          /* v-enter-active 表示入場動畫的時(shí)間段 */
          /* v-leave-active 表示離場動畫的時(shí)間段 */
          .div1-enter-active,
          .div1-leave-active {
            transition: all 0.8s ease;
          }
          /* v-enter 這個(gè)是一個(gè)時(shí)間點(diǎn),表示動畫進(jìn)入之前,元素的起始狀態(tài),此時(shí)還沒有進(jìn)入 */
          /* v-leave-to 這是一個(gè)時(shí)間點(diǎn),是動畫離開之后,元素的終止?fàn)顟B(tài),此時(shí),元素動畫已經(jīng)結(jié)束了 */
          .div2-enter,
          .div2-leave-to {
            opacity: 0;
            transform: translateX(50px);
          }
          
          /* v-enter-active 表示入場動畫的時(shí)間段 */
          /* v-leave-active 表示離場動畫的時(shí)間段 */
          .div2-enter-active,
          .div2-leave-active {
            transition: all 0.2s ease;
          }
        </style>

      十一、生命周期

      vue生命周期
      vue生命周期示意圖
      <!DOCTYPE html>
      <html>
      	<head>
      		<meta charset="utf-8" />
      		<title></title>
      		<script src="lib/vue-2.6.12.js"></script>
      	</head>
      	<body>
      		<div id="app">
      			<div id="divId">頁面還沒有渲染 --- {{msg}}</div>
      		</div>
      	</body>
      	<script>
      		var vue = new Vue({
      			el: '#app',
      			data: {
      				msg: '頁面渲染完畢'
      			},
      			methods: {},
      			filters: {},
      			beforeCreate() {
      				// 這是我們第一個(gè)遇到的生命周期函數(shù),實(shí)例被創(chuàng)建出來,還沒有data、methods等時(shí),會執(zhí)行它
      				let content = document.getElementById('divId')
      				console.log('beforeCreate:', content.innerText)
      				// 在js中,null和undefined是不同的含義。null表示有這個(gè)對象,但是這個(gè)對象的值是null。undefined表示壓根就沒有這個(gè)對象
      				console.log('beforeCreate', this.msg)
      			},
      			created() {
      				// Vue實(shí)例創(chuàng)建完畢,methods、data、filters等已經(jīng)掛載到vue實(shí)例上。如果需要調(diào)用methods,使用data,最早只能在這里操作
      				let content = document.getElementById('divId')
      				console.log('created', content.innerText)
      				console.log('created', this.msg)
      			},
      			beforeMount() {
      				// Vue實(shí)例創(chuàng)建完畢,頁面尚未重新渲染
      				let content = document.getElementById('divId')
      				console.log('beforeMounte', content.innerText)
      				console.log('beforeMounte', this.msg)
      			},
      			mounted() {
      				// 頁面渲染完畢
      				let content = document.getElementById('divId')
      				console.log('mounted', content.innerText)
      				console.log('mounted', this.msg)
      			}
      		})
      	</script>
      </html>

      十二、實(shí)戰(zhàn)演練

      案例一: 本地模擬員工信息的增刪改查功能。  源碼:  
      <!DOCTYPE html>
      <html>
      	<head>
      		<meta charset="utf-8" />
      		<title></title>
      		<!-- 引入layui樣式 -->
      		<link rel="stylesheet" href="lib/layui/css/layui.css" />
      		<!--引入vue.js-->
      		<script src="lib/vue-2.6.12.js"></script>
      		<!-- 引入layui.js -->
      		<script src="lib/layui/layui.all.js"></script>
      	</head>
      
      	<body>
      		<div id="app">
      			<fieldset class="layui-elem-field layui-field-title" style="margin-top: 20px;">
      				<legend>員工管理</legend>
      			</fieldset>
      			<!-- 搜索欄 -->
      			<form class="layui-form">
      				<div class="layui-form-item">
      					<div class="layui-inline">
      						<label class="layui-form-label">姓 名:</label>
      						<div class="layui-input-inline">
      							<input type="text" v-model="searchName" placeholder="請輸入姓名" class="layui-input">
      						</div>
      					</div>
      					<div class="layui-inline">
      						<button type="button" class="layui-btn layui-btn-normal  layui-icon layui-icon-search" @click="searchUser">查詢</button>
      						<button type="reset" class="layui-btn layui-btn-warm  layui-icon layui-icon-refresh">重置</button>
      						<button type="button" class="layui-btn layui-btn layui-icon layui-icon-addition" @click="saveOrUpdateDiv()">添加</button>
      					</div>
      				</div>
      			</form>
      
      			<!-- 數(shù)據(jù)表格 -->
      			<table class="layui-table">
      				<thead>
      					<tr>
      						<th>編號</th>
      						<th>姓名</th>
      						<th>年齡</th>
      						<th>性別</th>
      						<th>備注</th>
      						<th>操作</th>
      					</tr>
      				</thead>
      				<tbody>
      					<tr v-for="item in userList" :key="item.id">
      						<td>{{item.id}}</td>
      						<td>{{item.name}}</td>
      						<td>{{item.gender | handlerGender}}</td>
      						<td>{{item.remark}}</td>
      						<td>
      							<button type="button" class="layui-btn layui-btn-normal" @click="saveOrUpdateDiv(item)">編輯</button>
      							<button type="button" class="layui-btn layui-btn-danger" @click="delUser(item.id)">刪除</button>
      						</td>
      					</tr>
      				</tbody>
      			</table>
      
      			<!-- 添加和修改的彈出層開始 -->
      			<div style="display: none;padding: 20px" id="saveOrUpdateDiv">
      				<form class="layui-form">
      					<div class="layui-form-item">
      						<div class="layui-inline">
      							<label class="layui-form-label">用戶id</label>
      							<div class="layui-input-inline">
      								<input type="text" v-model="user.id" placeholder="輸入用戶id" class="layui-input" readonly>
      							</div>
      							<label class="layui-form-label">用戶姓名</label>
      							<div class="layui-input-inline">
      								<input type="text" v-model="user.name" placeholder="請輸入姓名" class="layui-input">
      							</div>
      						</div>
      					</div>
      					<div class="layui-form-item">
      						<div class="layui-inline">
      							<label class="layui-form-label">性別</label>
      							<div class="layui-input-inline">
      								<input type="text" v-model="user.gender" placeholder="請輸入性別" class="layui-input">
      							</div>
      							<label class="layui-form-label">備注</label>
      							<div class="layui-input-inline">
      								<input type="text" v-model="user.remark" placeholder="請輸入備注" class="layui-input">
      							</div>
      						</div>
      					</div>
      					<div class="layui-form-item" style="text-align: center;">
      						<div class="layui-input-block">
      							<button type="button" class="layui-btn layui-btn-normal layui-btn-sm layui-icon layui-icon-release" v-if="!user.id" @click="addUser">新增</button>
      							<button type="button" class="layui-btn layui-btn-normal layui-btn-sm layui-icon layui-icon-release" v-else @click="editUser(user)">修改</button>
      							<button type="reset" class="layui-btn layui-btn-warm layui-btn-sm layui-icon layui-icon-refresh">重置</button>
      						</div>
      					</div>
      				</form>
      			</div>
      			<!-- 添加和修改的彈出層結(jié)束 -->
      		</div>
      	</body>
      
      	<script>
      		var mainIndex;
      		const vm = new Vue({
      			el: '#app',
      			data: {
      				userList: [], //用戶列表
      				data: [ //數(shù)據(jù)庫,存放用戶數(shù)據(jù)
      					{ id: 1, name: '張三', gender: 1, remark: '姓張名三' },
      					{ id: 2, name: '李四', gender: 2, remark: '姓李名四' },
      					{ id: 3, name: '王五', gender: 1, remark: '姓王名五' },
      					{ id: 4, name: '趙六', gender: 2, remark: '姓趙名六' }
      				],
      				user: {},
      				searchName: '' //搜索用的名稱
      			},
      			filters: {
      				handlerGender(gender) {
      					if(gender == 1) {
      						return '男'
      					} else {
      						return '女'
      					}
      				}
      			},
      			methods: {
      				saveOrUpdateDiv(user) { //打開新增或者修改的彈出層
      					if(!user) {
      						title = '添加用戶';
      						//清空新增彈出層數(shù)據(jù)
      						this.user = {};
      					} else {
      						title = '編輯'+user.name+'信息';
      						//回顯編輯的數(shù)據(jù),注意不能直接 this.user = user;
      						this.user = { ...user };
      						//等價(jià)于this.user = {id: user.id, name: user.name,gender: user.gender,remark: user.remark}
      					}
      					mainIndex = layui.layer.open({
      						type: 1,
      						title: title,
      						content: layui.jquery("#saveOrUpdateDiv"),
      						area: ['700px', '250px'],
      						maxmin: true
      					});
      				},
      				getUserList(name) { //加載用戶數(shù)據(jù)
      					if(!name) {
      						name = '';
      					}
      					const dataList = this.data.filter(e => e.name.indexOf(name) >= 0);
      					this.userList = dataList;
      				},
      				addUser() { //添加用戶
      					const user = { ...this.user };
      					//等價(jià)于 const user = {id: this.user.id, name: this.user.name,gender: this.user.gender,remark: this.user.remark};
      					//隨機(jī)生成id,范圍在1-100之間
      					user.id = Math.round(Math.random() * (100 - 1) + 1)
      					//添加到數(shù)據(jù)庫里
      					this.data.push(user);
      					//關(guān)閉彈出層
      					layui.layer.close(mainIndex);
      					//重新加載數(shù)據(jù)
      					this.getUserList();
      				},
      				delUser(id) {
      					// 查到指定id所在數(shù)組索引下標(biāo)
      					const index = this.userList.findIndex(e => e.id === id)
      					// 刪除指定索引位置的數(shù)據(jù)
      					this.data.splice(index, 1)
      					// 刪除成功后,重新家在數(shù)據(jù)
      					this.getUserList()
      				},
      				editUser(user){ //修改用戶 
      					const index = this.data.findIndex(e => e.id === user.id);
      					this.data[index] = user;
      					//關(guān)閉彈出層
      					layui.layer.close(mainIndex);
      					//重新加載數(shù)據(jù)
      					this.getUserList();
      				},
      				searchUser() { // 搜索用戶
      					// 遍歷用戶,找到所有復(fù)合條件的用戶
      					this.getUserList(this.searchName)
      				}
      			},
      			created() {
      				// 進(jìn)入頁面,組件創(chuàng)建之后,獲取數(shù)據(jù)
      				this.getUserList()
      			}
      		})
      	</script>
      </html>
      測試結(jié)果:
      vue+layui增刪改查
      案例二: 本地模擬品牌管理的增刪改查功能。   源碼: 
      <!DOCTYPE html>
      <html lang="en">
      
      	<head>
      		<meta charset="UTF-8">
      		<meta http-equiv="X-UA-Compatible" content="IE=edge">
      		<meta name="viewport" content="width=device-width, initial-scale=1.0">
      		<title>品牌列表案例</title>
      		<!-- 引入bootstrap樣式-->
      		<link rel="stylesheet" href="lib/bootstrap.css">
      		<style>
      			body {
      				padding: 15px;
      				user-select: none;
      			}
      		</style>
      	</head>
      	<body>
      
      		<div id="app">
      			<!-- 卡片區(qū)域 -->
      			<div class="card">
      				<div class="card-header">
      					添加品牌
      				</div>
      				<div class="card-body">
      					<!-- 添加品牌的表單區(qū)域 -->
      					<!-- form 表單元素有 submit 事件 -->
      					<form @submit.prevent="add">
      						<div class="form-row align-items-center">
      							<div class="col-auto">
      								<div class="input-group mb-2">
      									<div class="input-group-prepend">
      										<div class="input-group-text">品牌名稱</div>
      									</div>
      									<input type="text" class="form-control" placeholder="請輸入品牌名稱" v-model.trim="brand">
      								</div>
      							</div>
      							<div class="col-auto">
      								<button type="submit" class="btn btn-primary mb-2">添加</button>
      							</div>
      						</div>
      					</form>
      				</div>
      			</div>
      
      			<!-- 表格區(qū)域 -->
      			<table class="table table-bordered table-hover table-striped">
      				<thead>
      					<tr>
      						<th scope="col">#</th>
      						<th scope="col">品牌名稱</th>
      						<th scope="col">狀態(tài)</th>
      						<th scope="col">創(chuàng)建時(shí)間</th>
      						<th scope="col">操作</th>
      					</tr>
      				</thead>
      				<tbody>
      					<tr v-for="item in list" :key="item.id">
      						<td>{{ item.id }}</td>
      						<td>{{ item.name }}</td>
      						<td>
      							<div class="custom-control custom-switch">
      								<!-- 使用 v-model 實(shí)現(xiàn)雙向數(shù)據(jù)綁定 -->
      								<input type="checkbox" class="custom-control-input" :id="'cb' + item.id" v-model="item.status">
      								<!-- 使用 v-if 結(jié)合 v-else 實(shí)現(xiàn)按需渲染 -->
      								<label class="custom-control-label" :for="'cb' + item.id" v-if="item.status">已啟用</label>
      								<label class="custom-control-label" :for="'cb' + item.id" v-else>已禁用</label>
      							</div>
      						</td>
      						<td>{{ item.time | dateFormat }}</td>
      						<td>
      							<a href="javascript:;" @click="remove(item.id)">刪除</a>
      						</td>
      					</tr>
      				</tbody>
      			</table>
      		</div>
      
      		<!-- 只要導(dǎo)入了 dayjs 的庫文件,在 window 全局,就可以使用 dayjs() 方法了 -->
      		<script src="./lib/dayjs.min.js"></script>
      		<script src="./lib/vue-2.6.12.js"></script>
      		<script>
      			// 聲明格式化時(shí)間的全局過濾器
      			Vue.filter('dateFormat', function(time) {
      				// 1. 對 time 進(jìn)行格式化處理,得到 YYYY-MM-DD HH:mm:ss
      				// 2. 把 格式化的結(jié)果,return 出去
      
      				// 直接調(diào)用 dayjs() 得到的是當(dāng)前時(shí)間
      				// dayjs(給定的日期時(shí)間) 得到指定的日期
      				const dtStr = dayjs(time).format('YYYY-MM-DD HH:mm:ss')
      				return dtStr
      			})
      
      			const vm = new Vue({
      				el: '#app',
      				data: {
      					// 用戶輸入的品牌名稱
      					brand: '',
      					// nextId 是下一個(gè),可用的 id
      					nextId: 4,
      					// 品牌的列表數(shù)據(jù)
      					list: [
      						{ id: 1, name: '寶馬', status: true, time: new Date() },
      						{ id: 2, name: '奔馳', status: false, time: new Date() },
      						{ id: 3, name: '奧迪', status: true, time: new Date() },
      					],
      				},
      				methods: {
      					show(item){
      						console.info(item)
      					},
      					// 點(diǎn)擊鏈接,刪除對應(yīng)的品牌信息
      					remove(id) {
      						this.list = this.list.filter(item => item.id !== id)
      					},
      					// 阻止表單的默認(rèn)提交行為之后,觸發(fā) add 方法
      					add() {
      						// 如果判斷到 brand 的值為空字符串,則 return 出去
      						if(this.brand === '') return alert('必須填寫品牌名稱!')
      
      						// 如果沒有被 return 出去,應(yīng)該執(zhí)行添加的邏輯
      						// 1. 先把要添加的品牌對象,整理出來
      						const obj = {
      							id: this.nextId,
      							name: this.brand,
      							status: true,
      							time: new Date()
      						}
      						// 2. 往 this.list 數(shù)組中 push 步驟 1 中得到的對象
      						this.list.push(obj)
      						// 3. 清空 this.brand;讓 this.nextId 自增 +1
      						this.brand = ''
      						this.nextId++
      					}
      				},
      			})
      		</script>
      	</body>
      </html>
      測試結(jié)果:
      vue+bootstrap增刪改查

      附件列表

         

        posted @ 2021-09-06 09:45  孤獨(dú)的星星  Views(83)  Comments(0)    收藏  舉報(bào)
        主站蜘蛛池模板: 中文字幕va一区二区三区| 伊人春色激情综合激情网| 久久超碰色中文字幕超清| 久久久久无码国产精品不卡| 亚洲AV无码秘?蜜桃蘑菇| 国产精品不卡一区二区三区| 中国农村真卖bbwbbw| 少妇上班人妻精品偷人| 成人av天堂男人资源站| 国产精品第一页中文字幕| 久久精品夜夜夜夜夜久久| 国产精品一区二区三区专区 | 一区二区三区国产亚洲网站| 亚洲一区二区约美女探花| 国产一区二区黄色在线观看| 电影在线观看+伦理片| 西西人体大胆444WWW| 亚洲欧美精品一中文字幕| 亚洲男人天堂av在线| 日本熟妇色xxxxx| 欧美性猛交xxxx乱大交极品| 国产丝袜在线精品丝袜| 精品国产一区av天美传媒| 黑人巨大亚洲一区二区久| 国产精品偷伦费观看一次| 口爆少妇在线视频免费观看| 国日韩精品一区二区三区| 中国老熟妇自拍hd发布| 亚洲国产精品成人av网| 好爽毛片一区二区三区四| 屁屁影院ccyy备用地址| 亚洲无?码A片在线观看| AV最新高清无码专区| 亚洲精品一区二区区别| 中年国产丰满熟女乱子正在播放| 亚洲国产99精品国自产拍| 99RE6在线观看国产精品| 日本一本无道码日韩精品| 伊在人间香蕉最新视频| 久久精品国产亚洲av久| 亚洲国产精品午夜福利|