1. 程式人生 > 程式設計 >深入瞭解Vue動態元件和非同步元件

深入瞭解Vue動態元件和非同步元件

1.動態元件

<!DOCTYPE html>
<html>
<head>
 <meta charset="utf-8">
 <style>
		#app {
			font-size: 0
		}
		.dynamic-component-demo-tab-button {
			padding: 6px 10px;
			border-top-left-radius: 3px;
			border-top-right-radius: 3px;
			border: 1px solid #ccc;
			cursor: pointer;
			margin-bottom: -1px;
			margin-right: -1px;
			background: #f0f0f0;
		}
		.dynamic-component-demo-tab-button.dynamic-component-demo-active {
			background: #e0e0e0;
		}
		.dynamic-component-demo-tab-button:hover {
			background: #e0e0e0;
		}
		.dynamic-component-demo-posts-tab {
			display: flex;					
		}
		.dynamic-component-demo-tab {
			font-size: 1rem;
			border: 1px solid #ccc;
			padding: 10px;
		}
		.dynamic-component-demo-posts-sidebar {
			max-width: 40vw;
			margin: 0 !important;
			padding: 0 10px 0 0 !important;
			list-style-type: none;
			border-right: 1px solid #ccc;
			line-height: 1.6em;
		}
		.dynamic-component-demo-posts-sidebar li {
			white-space: nowrap;
			text-overflow: ellipsis;
			overflow: hidden;
			cursor: pointer;
		}
		.dynamic-component-demo-active {
			background: lightblue;
		}
		.dynamic-component-demo-post-container {
			padding-left: 10px;
		}
		.dynamic-component-demo-post > :first-child {
			margin-top: 0 !important;
			padding-top: 0 !important;
		}
 </style>
 <script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
</head>
<body>
<div id="app">
	<button v-for="tab in tabs" class="dynamic-component-demo-tab-button" 
		v-bind:class="{'dynamic-component-demo-active': tab === currentTab}" 
		@click="currentTab = tab">{{ tab }}</button>	
	<keep-alive>
		<component v-bind:is="currentTabComponent"></component>
	</keep-alive>
</div>
<script>
 Vue.component('tab-posts',{
		data: function(){
			return {
				posts: [
					{id: 1,title: 'Cat Ipsum',content: 'Cont wait for the storm to pass,...'},{id: 2,title: 'Hipster Ipsum',content: 'Bushwick blue bottle scenester ...'},{id: 3,title: 'Cupcake Ipsum',content: 'Icing dessert souffle ...'},],selectedPost: null
			}
		},template: `<div class="dynamic-component-demo-posts-tab dynamic-component-demo-tab">
						<ul class="dynamic-component-demo-posts-sidebar">
							<li v-for="post in posts" 
								v-bind:key="post.id" 
								v-on:click="selectedPost = post" 
								v-bind:class="{'dynamic-component-demo-active': post===selectedPost}">
								{{ post.title }}
							</li>
						</ul>
						<div class="dynamic-component-demo-post-container">
							<div v-if="selectedPost" class="dynamic-component-demo-post">
								<h3>{{ selectedPost.title }}</h3>
								<div v-html="selectedPost.content"></div>
							</div>
							<strong v-else>
								Click on a blog title to the left to view it.
							</strong>
						</div>
					</div>`
 });
	
	Vue.component('tab-archive',{
		template: '<div class="dynamic-component-demo-tab">Archive component</div>'
	});

 new Vue({
 el: '#app',data: {
			currentTab: 'Posts',tabs: ['Posts','Archive']
		},computed: {
			currentTabComponent: function(){
				return 'tab-' + this.currentTab.toLowerCase()
			}
		}
 });
</script>
</body>
</html>

深入瞭解Vue動態元件和非同步元件

在動態元件上使用keep-alive,可以在元件切換時保持元件的狀態,避免了重複渲染的效能問題。

2.非同步元件

Vue 允許你以一個工廠函式的方式定義你的元件,這個工廠函式會非同步解析你的元件定義。

Vue.component('async-example',function (resolve,reject) {})

這裡可以回顧一下 Vue.js — 元件基礎。

我們使用通過webpack打包的Vue專案來介紹非同步元件。

<!-- HelloWorld.vue -->
<template>
 <div>
 <h2 class="title">{{msg}}</h2>
 </div>
</template>

<script>
export default {
 data () {
 return {
 msg: 'Hello Vue!'
 }
 }
}
</script>

<!-- Add "scoped" attribute to limit CSS to this component only -->
<style scoped>
 .title {
 padding: 5px;
 color: white;
 background: gray;
 }
</style>
<!-- App.vue -->
<template>
 <div id="app">
 <HelloWorld/>
 </div>
</template>

<script>
import HelloWorld from './components/HelloWorld'

export default {
 name: 'App',components: {
 HelloWorld
 }
}
</script>

<style>
</style>

我們把App.vue的<script>標籤裡面的內容改為:

export default {
 name: 'App',components: {
 HelloWorld: () => import('./components/HelloWorld')
 }
}

這樣就實現了App元件非同步載入HelloWorld元件的功能。

我們可以實現按需載入。

<!-- App.vue -->
<template>
 <div id="app">
 <button @click="show = true">Load Tooltip</button>
 <div v-if="show">
 <HelloWorld/>
 </div>
 </div>
</template>

<script>
export default {
 data: () => ({
 show: false
 }),components: {
 HelloWorld: () => import('./components/HelloWorld')
 }
}
</script>

<style>
</style>

這裡的非同步元件工廠函式也可以返回一個如下格式的物件:

const AsyncComponent = () => ({
 // 需要載入的元件 (應該是一個 `Promise` 物件)
 component: import('./MyComponent.vue'),// 非同步元件載入時使用的元件
 loading: LoadingComponent,// 載入失敗時使用的元件
 error: ErrorComponent,// 展示載入時元件的延時時間。預設值是 200 (毫秒)
 delay: 200,// 如果提供了超時時間且元件載入也超時了,
 // 則使用載入失敗時使用的元件。預設值是:`Infinity`
 timeout: 3000
})

參考:

動態元件 & 非同步元件 — Vue.js

以上就是深入瞭解Vue動態元件和非同步元件的詳細內容,更多關於Vue動態元件和非同步元件的資料請關注我們其它相關文章!