版權(quán)說明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請進(jìn)行舉報(bào)或認(rèn)領(lǐng)
文檔簡介
第5章-Vue.js組件開發(fā)(4學(xué)時(shí))教學(xué)目標(biāo)熟悉組件的命名規(guī)范。掌握全局、局部注冊組件的方法。掌握組件間常用的通信方法。掌握插槽的分類和定義方法。15.1組件基礎(chǔ)
組件(Component)是Vue.js最強(qiáng)大的功能之一。組件可以擴(kuò)展HTML元素,封裝可重用的代碼。組件也可以看作為自定義的HTML元素。可以使用獨(dú)立可復(fù)用的小組件來構(gòu)建大型應(yīng)用,幾乎任意類型的應(yīng)用的界面都可以抽象為一個(gè)組件樹,如圖所示。5.1.1組件命名
組件注冊前必須給組件命名,組件名應(yīng)該采用多個(gè)單詞構(gòu)成,以免與現(xiàn)有的或未來的HTML元素有沖突。由于所有的HTML元素名稱都是由單個(gè)單詞構(gòu)成。Vue組件中通常采用kebab-case(短橫線分隔式)或camelCase(駝峰式)命名方式。(1)kebab-case-命名法
當(dāng)使用kebab-case定義一個(gè)組件時(shí),必須在引用自定義元素時(shí)使用kebab-case命名方式。Vueprops命名最好直接使用kebab-case命名。例如my-name、my-component-name等。(2)camelCase命名法
camelCase(也稱為駝峰式)命名法就是當(dāng)組件名稱是由一個(gè)或多個(gè)單詞構(gòu)成時(shí),第一個(gè)單詞首字母以小寫字母開始,從第二個(gè)單詞開始以后的每個(gè)單詞的首字母都采用大寫字母。例如:myFirstName、myLastName、myComponent。注意,盡管如此,直接在DOM(即非字符串的模板)中使用時(shí),只有kebab-case是有效的。(3)PascalCase(帕斯卡命名)
與camelCase相比,PascalCase命名時(shí),第一個(gè)單詞的首字母是大寫的;但camelCase命名時(shí),第一個(gè)單詞的首字母小寫。當(dāng)使用PascalCase命名法定義一個(gè)組件時(shí),在引用自定義元素時(shí)兩種命名法都可以使用。也就是說<my-component-name>和<MyComponentName>都是可接受的。
因?yàn)镠TML不區(qū)分大小寫,所以不管是用Kebab-case還是camelCase命名的組件在寫入HTML后都要改寫為Kebab-case格式。5.1組件基礎(chǔ)5.1組件基礎(chǔ)組件命名基本語法//在組件定義中components:{//使用kebab-case注冊'kebab-cased-component':{/*...*/},//使用camelCase注冊'camelCaseComponent':{/*...*/},//使用PascalCase注冊'PascalCasedComponent':{/*...*/}}在HTML模板中,請使用kebab-case:<!--在HTML模板中始終使用kebab-case--><kebab-cased-component></kebab-cased-component><camel-cased-component></camel-cased-component><pascal-cased-component></pascal-cased-component>//組件中定義components:{'kebab-cased-component':{/*...*/},'camelCaseComponent':{/*...*/},'PascalCasedComponent':{/*...*/}}//在字符串模板中,可以采用以下格式引用constapp=Vue.createApp({});ponent('MyCom',{template:`<div><kebab-cased-component></kebab-cased-component><camel-cased-component></camel-cased-component><camelCaseComponent></camelCaseComponent><pascal-cased-component></pascal-cased-component><pascalCasedComponent></pascalCasedComponent><PascalCasedComponent></PascalCasedComponent></div>`})5.1.2組件注冊
組件注冊通常分為全局注冊和局部注冊。全局組件適用于所有實(shí)例,局部組件僅供本實(shí)例使用。1.全局注冊組件的定義【基本語法】//全局組件注冊constapp=Vue.createApp({})ponent(tagName,options)//直接定義選項(xiàng)
ponent('myComponet',{//data必須定義為函數(shù),并通過return返回相關(guān)數(shù)據(jù)template:'HTML元素定義'})//也可以鏈?zhǔn)阶匀纸M件app.component('ComponentA',ComponentA).component('ComponentB',ComponentB).component('ComponentC',ComponentC)
一個(gè)組件的data選項(xiàng)必須是一個(gè)函數(shù),因此每個(gè)實(shí)例可以維護(hù)一份被返回對象的獨(dú)立的拷貝。
與Vue實(shí)例中data選項(xiàng)的定義方法不同。在組件中定義data選項(xiàng)時(shí),必須定義為函數(shù),其中的數(shù)據(jù)通過return返回。具體格式如下:data:function(){return{//定義相關(guān)數(shù)據(jù)屬性}}data(){return{}}//同樣生效。
注冊后,可以調(diào)用組件。調(diào)用方式如下:<tagName></tagName>
在Vue實(shí)例中,必須通過components選項(xiàng)來定義自己的組件。也可以使用普通的JavaScript對象來定義組件,然后在全局注冊和局部注冊時(shí)直接引用?!净菊Z法】constcomponentA={template:'<h1>h1-Js自定義局部組件-A組件</h1>'};//創(chuàng)建Vue實(shí)例const{createApp}=Vue;constApp={//定義根組件components:{//局部注冊子組件mycomp1:componentA, mycomp2:tmp1}}) createApp(App).mount('#app');//也可以采用以下方法createApp({components:{mycomp1:componentA, mycomp2:tmp1}}).mount('#app');2.局部注冊組件的定義【語法說明】
局部注冊時(shí),需要在components選項(xiàng)下注冊組件,mycomp1、mycomp2為組件名,componentA組件對應(yīng)的JS對象或選項(xiàng)對象。在Vue里,一個(gè)組件本質(zhì)上是一個(gè)擁有預(yù)定義選項(xiàng)的一個(gè)Vue實(shí)例,在Vue中注冊組件非常簡單?!纠?-1】組件注冊實(shí)戰(zhàn)<divid="app">
<fieldset>
<legend>定義全局組件與復(fù)用</legend>
<my-com></my-com>
<my-com></my-com>
<my-com></my-com>
</fieldset>
<fieldset>
<legend>定義全局組件</legend>
<mycomp2></mycomp2>
</fieldset>
<fieldset>
<legend>定義局部組件</legend>
<mycomp1></mycomp1>
</fieldset>
</div>
<scripttype="text/javascript">
const{createApp}=Vue;//解構(gòu)賦值createApp
//定義JS對象componentA
varcomponentA={
template:"<h1>h1-Js自定義局部組件-A組件</h1>",
};//定義JS對象componentB
varcomponentB={
data(){
return{title:"我自己定義的標(biāo)題信息!"
};
},
template:`
<div>
<p>多個(gè)HTML元素時(shí),使用根元素div</p>
<h3v-bind:title="title">h3-Js自定義全局組件-B組件,盤旋會(huì)有提示</h3>
</div>`,
};【例5-1】組件注冊實(shí)戰(zhàn)//局部注冊組件mycomp1
constApp={
components:{mycomp1:componentA},
};
constapp1=createApp(App);
//全局注冊組件my-com,定義1個(gè)計(jì)算器的按鈕
ponent("my-com",{
data(){return{count:0};
},
template:'<buttonv-on:click="count++">單擊{{count}}次按鈕</button>',
});
//通過JavaScript對象componentB來定義mybutton2組件
ponent("mycomp2",componentB);
//定義App組件,并在根組件中注冊子組件mybutton1
app1.mount("#app");//掛載
</script>5.2組件間通信
在Vue中,父子組件的關(guān)系可以總結(jié)為“props向下傳遞,事件向上傳遞”。父組件通過props給子組件下發(fā)數(shù)據(jù),子組件通過事件給父組件發(fā)送消息,如圖5-3所示。子組件需要顯式地用defineProps()函數(shù)聲明props。props的值可以是兩種:一種是字符串?dāng)?shù)組,一種是對象。1.使用props傳遞數(shù)據(jù)【基本語法】<!--HTML模板部分--><divid="app"><my-componentmessage="父組件通過props傳遞參數(shù)"></my-component></div><!--JS部分--><scripttype="text/javascript">constapp=Vue.createApp({});//組件定義ponent('my-component',{props:['message'],template:'<div>{{message}}</div>'});App.mount('#app');</script>5.2.1父組件向子組件傳值【語法說明】<my-component></my-component>為自定義組件,采用kebab-case格式命名,相當(dāng)于一個(gè)HTML元素。message為組件的屬性,其值作為傳遞給子組件的內(nèi)容。props屬性為字符串?dāng)?shù)組(用[]包圍),其中的屬性必須使用引號('message')包圍,可以在模板通過文本插值的方式來使用。此種父子組件通信是單向的。組件中的數(shù)據(jù)共有3種形式:data、props、computed。注意:組件中data與props屬性的區(qū)別。
組件中data和props都可以為組件提供數(shù)據(jù),但它們是有區(qū)別的。data選項(xiàng)的類型為對象類型,對象中return出去的數(shù)據(jù)屬于組件內(nèi)部數(shù)據(jù),只能用于為組件本身。props選項(xiàng)的類型可以是字符串?dāng)?shù)組,也可以是對象。用來聲明組件從外部接收的數(shù)據(jù)。此兩種數(shù)據(jù)都可以在template模板、計(jì)算屬性computed和方法methods中使用。5.2.1父組件向子組件傳值5.2.1父組件向子組件傳值-2組件中使用props接收父組件message屬性傳遞過來的數(shù)據(jù)。2.靜態(tài)props傳遞數(shù)據(jù)HTML中的屬性名是大小寫不敏感的,所以瀏覽器會(huì)把所有大寫字符解釋為小寫字符。這意味著當(dāng)使用DOM中的模板時(shí),camelCase的prop名稱需要使用其等價(jià)的kebab-case命名。
通常父組件單向(正向)傳遞數(shù)據(jù)給子組件。需要三個(gè)步驟:(1)創(chuàng)建父、子組件構(gòu)造器。通過Vue.extend()方法構(gòu)建組件。(2)注冊父、子組件??梢匀只蚓植孔愿黝惤M件。(3)在Vue實(shí)例范圍內(nèi)使用組件。5.2.1父組件向子組件傳值-3【例5-3】靜態(tài)props傳遞數(shù)據(jù)實(shí)戰(zhàn)。5.2.1父組件向子組件傳值-4第18~29行定義Vue實(shí)例,并設(shè)置el、data選項(xiàng),myToDos對象數(shù)組準(zhǔn)備數(shù)據(jù)。第33~49行定義兩個(gè)組件,分別為todoChid、todoParent,并在todoParent組件中局部注冊子組件todoChild為“todoItem”。第51行將組件todoParent注冊為全局組件“mytodo”。3.動(dòng)態(tài)Props傳遞數(shù)據(jù)
要?jiǎng)討B(tài)地綁定父組件的數(shù)據(jù)到子模板的props,與綁定到任何普通的HTML屬性相類似,就是用v-bind。每當(dāng)父組件的數(shù)據(jù)發(fā)生變化時(shí),都會(huì)實(shí)時(shí)地將變化后的數(shù)據(jù)傳遞給子組件?!纠?-4】動(dòng)態(tài)Props傳遞數(shù)據(jù)實(shí)戰(zhàn)。5.2.1父組件向子組件傳值-55.2.1父組件向子組件傳值-6第40~44行注冊全局組件my-component-1,在組件內(nèi)的模板屬性中定義文本輸入框,采用v-model綁定message屬性。第18行引用組件my-component-1,此時(shí)在組件中修改props傳遞過來的數(shù)據(jù),Vue會(huì)發(fā)出警告,如圖5-7所示。所以通常采用computed計(jì)算屬性去修改props傳遞過來的值。本地定義屬性,并將props作為初始值,props傳入之后需要進(jìn)行轉(zhuǎn)換,此時(shí)使用代碼中第27~32行的定義即實(shí)現(xiàn)此功能?!纠?-5】傳值時(shí)v-bind使用問題注意:在使用props對子組件傳值時(shí),如果不使用v-bind傳遞數(shù)字、布爾、數(shù)組、對象類型的數(shù)據(jù),此時(shí)傳遞的數(shù)據(jù)都是字符串類型,由于模板中未使用v-bind指令綁定屬性,不會(huì)被編譯。第12行通過v-bind綁定message,將屬性值作為數(shù)組,所以長度為4。第14行未通過v-bind綁定message,將屬性值作為字符串,所以長度為17。4.Props數(shù)據(jù)驗(yàn)證
組件props選項(xiàng)的值可以是數(shù)組類型,也可以是對象類型。props選項(xiàng)的對象類型可以用于對外部傳遞進(jìn)來的參數(shù)進(jìn)行數(shù)據(jù)驗(yàn)證。當(dāng)封裝了一個(gè)組件時(shí),對于內(nèi)部接收的參數(shù)進(jìn)行校驗(yàn)是非常必要的。default:表示默認(rèn)值。required:必選。
//如果是數(shù)組或?qū)ο螅J(rèn)值必須是一個(gè)函數(shù)來返回
propE:
{
type:
Array,
default:
function
()
{
return
{};
}
},
//自定義驗(yàn)證函數(shù)
propF:
{
viladator:
function
(value)
{
return
value
>
10;
}
}
}
});
</script>
<script>
Vponent('my-comp',{
props:{
//必須是數(shù)字類型
propA:
Number,
//必須是字符串或數(shù)字類型
propB:[String,
Number],
//布爾值,如果沒有定義,默認(rèn)值就是true
propC:{
type:
Boolean,
default:
true
},
//數(shù)字,而且是必選
propD:
{
type:
Number,
required:
true
},
驗(yàn)證的type類型可以是:String、Number、Boolean、Object、Array、Function。type也可以是一個(gè)自定義構(gòu)造器,使用instanceof檢測。prop驗(yàn)證失敗時(shí),開發(fā)版本下會(huì)在控制臺拋出一條警告。【例5-6】props數(shù)據(jù)驗(yàn)證5.2.2子組件向父組件傳值1.自定義事件
當(dāng)子組件需要向父組件傳遞數(shù)據(jù)時(shí),需要使用自定義事件。子組件用$emit()來觸發(fā)自定義事件,父組件使用$on()來監(jiān)聽子組件的事件。父組件也可以直接在子組件的自定義標(biāo)記上使用v-on指令來監(jiān)聽子組件觸發(fā)的自定義事件。數(shù)據(jù)就通過自定義事件來傳遞。父組件v-on:自定義事件,傳遞數(shù)據(jù)<child-compv-on:eventName="functionName"></child-comp>//父組件中的Vue實(shí)例中定義methods選項(xiàng)
methods:{functionName(postdata){//將傳遞來的數(shù)據(jù)postdata進(jìn)行處理,并對父組件的數(shù)據(jù)進(jìn)行運(yùn)算}}子組件$emit()觸發(fā)自定義事件,傳遞數(shù)據(jù)<button@click='increase'>增加1</button>methods:{'increase':function(){
this.$emit('eventName',data);},…} 【語法說明】子組件通過this.$emit("eventName",data)方式來調(diào)用父組件中的functionName方法,同時(shí)子組件傳遞數(shù)據(jù)給父組件。父組件使用v-on:xxx(@xxx)來監(jiān)聽自定義事件。需要注意$emit()函數(shù)的第一個(gè)參數(shù)是自定義事件的名稱,第二個(gè)參數(shù)為數(shù)據(jù),數(shù)據(jù)可以有多個(gè)。
【例5-7】子組件向父組件傳遞數(shù)據(jù)【例5-7】子組件向父組件傳遞數(shù)據(jù)第39~51行定義父組件,并通過子組件<my-comp>來監(jiān)聽自定義事件increase、reduce,當(dāng)事件發(fā)生時(shí)調(diào)用changeTotal方法實(shí)現(xiàn)傳值。代碼第55~79行定義子組件,在子組件template標(biāo)記內(nèi)定義兩個(gè)按鈕定義單擊事件,來處理子組件的數(shù)據(jù),并將子組件的數(shù)據(jù)傳出。
5.2.2子組件向父組件傳值5.2.2子組件向父組件傳值2.使用v-model
由于Vue3.x中v-model使用方法已經(jīng)變更。用于自定義組件時(shí),v-modelprop和事件默認(rèn)名稱已更改為以下格式:prop:value->modelValue;event:input->update:modelValue;
在父組件上使用v-model:modelValue='xxx‘指令,子組件中使用this.$emit('update:modelValue',this.子組件屬性)。
父組件中通過v-model指令綁定數(shù)據(jù)modelValue<divid="app"><my-compv-model:modelValue=modelValue'></my-comp></div>子組件中通過事件觸發(fā)$emit(‘update:modelValue’,data)constapp=Vue.createApp(App);ponent('my-comp',{ template:` <divclass='childClass'> <button@click='increase'>增加1</button> </div>`,methods:{ increase(){//計(jì)數(shù)器增1this.counter++;this.$emit('update:modelValue',this.counter); },}})【例5-8】v-model指令傳遞數(shù)據(jù)第39~47行定義父組件,并通過子組件my-comp設(shè)置v-model指令綁定父組件的total屬性來處理“update:total”事件發(fā)生接收來自子組件的數(shù)據(jù)this.amount(相當(dāng)于total=this.counter)?!纠?-8】v-model指令傳遞數(shù)據(jù)代碼第49~73行定義子組件,在子組件template標(biāo)記內(nèi)定義兩個(gè)按鈕定義單擊事件,來處理子組件的數(shù)據(jù),并將子組件的數(shù)據(jù)傳出。5.2.3父鏈與子組件索引
采用父鏈和子組件索引同樣可以實(shí)現(xiàn)組件間通信。
在子組件中,使用this.$parent可以直接訪問該組件的父實(shí)例或組件,父組件也可以通過this.$children訪問它所有的子組件,而且可以遞歸向上或向下無限訪問,直到根實(shí)例或最內(nèi)層的組件。1.父鏈(this.$parent)實(shí)現(xiàn)修改父組件數(shù)據(jù)。2.子組件索引(this.$refs.indexName)修改組件數(shù)據(jù)。1.子組件利用父鏈this.$parent來獲取設(shè)置父組件的數(shù)據(jù)。部分代碼如下:constmsg=this.$parent.message;//獲取數(shù)據(jù)this.$parent.message
=
'消息:組件my-comp修改數(shù)據(jù)'
//設(shè)置父組件的數(shù)據(jù)
2.子組件索引this.$refs.indexName修改組件數(shù)據(jù)。部分代碼如下:<my-comp1
ref="comp1"></my-comp1>
<my-comp2
ref="comp2"></my-comp2>
//在事件處理函數(shù)中或JS代碼中this.message
=
this.$p1.message;
//通過$refs獲取子組件的數(shù)據(jù)this.$p1.message=this.message
//通過$refs設(shè)置子組件的數(shù)據(jù)
注意:$refs只在組件渲染完成后才填充,并且它是非響應(yīng)式的。5.2.4父鏈與子組件索引5.4插槽
在開發(fā)組件時(shí),組件內(nèi)一些子元素希望是由調(diào)用者來定義,組件只負(fù)責(zé)核心功能,其他非核心可以用戶自由定義,可以增加組件的靈活性和可擴(kuò)展性。這種的場景非常適合使用插槽。
插槽(Slot)是Vue提出來的一個(gè)概念,用于決定將所攜帶的內(nèi)容插入到指定的某個(gè)位置,從而使模板分塊,具有模塊化的特點(diǎn)和更大的重用性。
插槽顯不顯示、怎樣顯示是由父組件來控制的,而插槽在哪里顯示就由子組件來進(jìn)行控制,父頁面在組件標(biāo)記內(nèi)插入任意內(nèi)容,子組件內(nèi)插槽slot控制擺放位置(匿名插槽、具名插槽)。插槽分類:
(1)匿名插槽:也稱為默認(rèn)插槽default。沒有命名,有且只有一個(gè)。
(2)具名插槽:相對匿名插槽組件slot標(biāo)記帶name命名的。
(3)作用域插槽:子組件內(nèi)數(shù)據(jù)可以被父頁面拿到(解決了數(shù)據(jù)只能從父頁面?zhèn)鬟f給子組件)。5.4.1匿名插槽
匿名插槽通常也稱為“默認(rèn)插槽”。使用<slot></slot>元素來為需要傳遞的內(nèi)容占個(gè)位置,類似于內(nèi)容占位符?!净A(chǔ)語法】
(1)父組件中使用子組件標(biāo)記,并攜帶傳遞的內(nèi)容。
<child><p>父組件需要分發(fā)給子組件的內(nèi)容...</p></child>
(2)子組件中模板中插入插槽標(biāo)記。constComp1={template:`<divclass="comp"> <h3>這是子組件...</h3> <slot></slot> <slot></slot> … </div>`}//Vue實(shí)例中注冊子組件constApp={
components:{
child:Comp1,
},
};反引號【語法說明】
子組件渲染時(shí),會(huì)將slot標(biāo)記使用父組件中子組件標(biāo)記的內(nèi)容所替換。子組件中如果有多個(gè)默認(rèn)插槽,將會(huì)同時(shí)被父組件傳遞的內(nèi)容所替換。如果在子組件的模板中沒有插入slot標(biāo)記的話,則父組件中使用子組件標(biāo)記的內(nèi)容將被忽略?!纠?-10】默認(rèn)插槽的使用5.4.2具名插槽slot元素可以用一個(gè)特殊的屬性name來配置如何分發(fā)內(nèi)容,多個(gè)slot可以有不同的名字,根據(jù)具名slot的name來進(jìn)行匹配,顯示內(nèi)容。
如果有匿名slot,那么沒有匹配到的內(nèi)容將會(huì)顯示到匿名slot中;如果沒有匿名slot,那么沒有匹配到的內(nèi)容將會(huì)被拋棄。
在向具名插槽提供內(nèi)容的時(shí)候,也可以在一個(gè)template元素上使用v-slot指令,并以v-slot的參數(shù)的形式提供其名稱(如v-slot:slotname)。template元素中的所有內(nèi)容都將會(huì)被傳入相應(yīng)的插槽中。任何沒有被包裹在帶有v-slot的template元素中的內(nèi)容都會(huì)被視為匿名插槽的內(nèi)容。當(dāng)然也可以在一個(gè)template元素中包裹匿名(默認(rèn))插槽的內(nèi)容?!净菊Z法】(1)在父組件中的子組件標(biāo)記內(nèi),使用帶slot屬性的標(biāo)記或帶v-slot指令參數(shù)的template元素來攜帶傳遞的內(nèi)容。<child><p>該內(nèi)容將顯示在匿名插槽中。</p><template><p>使用匿名插槽--該內(nèi)容將顯示在匿名插槽中。</p></template><templatev-slot:slot1|#slot1><p>使用v-slot指令--該內(nèi)容將顯示在具名插槽slot1中。</p></template><pslot='slot2'>使用slot屬性--該內(nèi)容將顯示在具名插槽slot2中。</p></child>(2)子組件中模板中插入具名插槽標(biāo)記(使用name屬性)。constComp1={ template:` <divclass="comp"> <h3>這是子組件...</h3> <slotname='slot1'></slot> <slotname='slot2'></slot> <slot></slot> </div> `}//Vue實(shí)例中注冊子組件components:{'child':Comp1,}5.4.2具名插槽【語法說明】
父組件中使用子組件標(biāo)記,并在其中插入多個(gè)帶slot屬性的標(biāo)記,其屬性值為子組件中定義slot元素所指定的name屬性值。子組件渲染時(shí),匹配到slot元素(name的屬性值)會(huì)被父組件中子組件標(biāo)記的內(nèi)具有相應(yīng)的slot屬性值的標(biāo)記的內(nèi)容所替換。在父組件中可以使用帶“v-slot:slotname”參數(shù)的template元素來攜帶傳遞內(nèi)容,同樣會(huì)匹配到帶name屬性的具名插槽。V-slot:slot1等價(jià)于#slot1,這叫語法糖【例5-11】具名插槽與匿名插槽混合使用5.4.3作用域插槽Vue2.6.0引入v-slot指令,提供支持slot和slot-scope屬性的API替代方案。作用域插槽可用作一個(gè)能被傳遞數(shù)據(jù)的可重用模版。
匿名插槽和具名插槽的內(nèi)容和樣式皆由父組件決定,即顯示什么內(nèi)容和怎樣顯示都由父組件決定;作用域插槽的樣式由父組件決定,內(nèi)容卻由子組件控制。簡單來說:前兩種插槽不能綁定數(shù)據(jù),作用域插槽是一個(gè)帶綁定數(shù)據(jù)的插槽。獲取子組件slot中攜帶的數(shù)據(jù)的關(guān)鍵步驟:
(1)在slot元素上使用v-bind指令綁定一個(gè)特定屬性,這個(gè)屬性稱為插槽prop。<slotv-bind:customAttribute="childDataOptions"></slot>customAttribute:為用戶自定義的屬性,為父組件提供數(shù)據(jù)對象;childDataOptions:為子組件data中的屬性或?qū)ο蟆?/p>
(2)在父組件上訪問綁定到slot插槽上的prop對象。<templatev-slot:default|slotname="slotProps"> <p>來自父組件的內(nèi)容</p> <p>{{slotProps.customAttribute}}</p></template>【例5-12】作用域插槽的應(yīng)用第37~54行全局定義子組件child,在模板選項(xiàng)中插入插槽,綁定item屬性,循環(huán)遍歷items數(shù)組變量中的所有數(shù)據(jù),其中v-for=‘item
in
items’中的item是臨時(shí)變量。而綁定在插槽slot元素上的item屬性稱為“插槽prop”,在父級作用域中,可以使用帶值的v-slot來定義子組件提供的插槽prop的名字,方法如第30行中{{props.item.id}}等。
【例5-13】作用域插槽的應(yīng)用5.4.4動(dòng)態(tài)插槽名
動(dòng)態(tài)指令參數(shù)也可以用在v-slot上,來定義動(dòng)態(tài)的插槽名。部分示例代碼如下:<my-child>
<template
v-slot:[dynamicSlotName]>
...
</template>
</my-child>
動(dòng)態(tài)插槽名需要使用“[]”來包裹,dynamicSlotName是一個(gè)變量,然后在Vue實(shí)例的data選項(xiàng)中定義動(dòng)態(tài)插槽名,并給其賦初值。通過其他事件來改變動(dòng)態(tài)插槽名,達(dá)到動(dòng)態(tài)渲染子組件?!纠?-13】動(dòng)態(tài)插槽名的應(yīng)用。【例5-13】動(dòng)態(tài)插槽名的應(yīng)用本章小結(jié)本章主要介紹了組件基礎(chǔ)、組件間通信和插槽的基礎(chǔ)概念和基本使用語法。組件基礎(chǔ)中重點(diǎn)介紹了組件的命名規(guī)范和注冊方法。Vue組件中通常采用camelCase(駝峰式)命名或kebab-case(短橫線分隔式)命名方式。組件可以全局注冊ponent(),也可以局部注冊(在App內(nèi)通過components選項(xiàng)中注冊)。重點(diǎn)講解了匿名插槽、具名插槽、作用域插槽及動(dòng)態(tài)插槽名的應(yīng)用場景和基本語法。思考與拓展總結(jié)與提高本章小結(jié)組件間通信主要講解了父組件向子組件傳值、子組件向父組件傳值和兄弟組件之間通信等。在子組件中使用props來使用父組件傳遞過來的數(shù)據(jù),這是單向傳遞,只能從父組向子組件傳遞。子組件用$emit()來觸發(fā)自定義事件,父組件通過$on()或v-on:eventname來監(jiān)聽子組件的事件,父組件也可以使用v-model指令通過input事件來傳遞數(shù)據(jù)。當(dāng)然也可以通過父鏈與子組件索引來傳遞數(shù)據(jù)。插槽主要講解了匿名插槽、具名插槽(設(shè)置name屬性)、作用域插槽(v-slot:slotname或slot-scope=‘Props’)以及動(dòng)態(tài)插槽名(v-slot:[dynslot])等方面的父子組件數(shù)據(jù)傳遞的方法。思考與拓展總結(jié)與提高40思政第6章-Vue.js過渡與動(dòng)畫(4學(xué)時(shí))教學(xué)目標(biāo)1.熟悉過渡類名的含義和命名規(guī)范。2.掌握單元素/單組件的過渡方法。3.掌握初始渲染過渡的方法。4.掌握列表進(jìn)入/離開、排序和交錯(cuò)過渡的實(shí)現(xiàn)方法。5.學(xué)會(huì)編寫帶有Vue.js過渡和動(dòng)畫效果的頁面。416.1單元素/組件的過渡Vue在插入、更新或者移除DOM時(shí),提供多種不同方式的應(yīng)用過渡效果。包括以下工具:(1)在CSS過渡和動(dòng)畫中自動(dòng)應(yīng)用class。(2)可以配合使用第三方CSS動(dòng)畫庫,如Animate.css。(3)在過渡鉤子函數(shù)中使用JavaScript直接操作DOM。(4)可以配合使用第三方JavaScript動(dòng)畫庫,如Velocity.js。Vue提供了內(nèi)置的過渡封裝組件,該組件用于包裹要實(shí)現(xiàn)過渡效果的組件。Vue提供了<transition>的封裝組件,可以給任何元素和組件添加進(jìn)入/離開過渡。Vue的transiton標(biāo)記的語法:<transition
name="slide-fade">
<div>
<p
v-if="flag"><img
src="image-6-1.jpg"></p>
</div>
</transition>
使用情形如下:(1)條件渲染(使用v-if)(2)條件展示(使用v-show)(3)動(dòng)態(tài)組件(4)組件根節(jié)點(diǎn)【例6-1】單元素(圖像)過渡實(shí)戰(zhàn)6.1.1過渡的類名
在進(jìn)入/離開的過渡中,會(huì)有6個(gè)class切換(v代表在沒有transitionname的時(shí)候調(diào)用)。(1)v-enter-from:定義進(jìn)入過渡的開始狀態(tài)。在元素被插入之前生效,在元素被插入之后的下一幀移除。(2)v-enter-active:定義進(jìn)入過渡生效時(shí)的狀態(tài)。在整個(gè)進(jìn)入過渡的階段中應(yīng)用,在元素被插入之前生效,在過渡/動(dòng)畫完成之后移除。這個(gè)類可以被用來定義進(jìn)入過渡的過程時(shí)間,延遲和曲線函數(shù)。(3)v-enter-to:定義進(jìn)入過渡的結(jié)束狀態(tài)。在元素被插入之后下一幀生效(與此同時(shí)v-enter被移除),在過渡/動(dòng)畫完成之后移除。(4)v-leave-from:定義離開過渡的開始狀態(tài)。在離開過渡被觸發(fā)時(shí)立刻生效,下一幀被移除。(5)v-leave-active:定義離開過渡生效時(shí)的狀態(tài)。在整個(gè)離開過渡的階段中應(yīng)用,在離開過渡被觸發(fā)時(shí)立刻生效,在過渡/動(dòng)畫完成之后移除。這個(gè)類可以被用來定義離開過渡的過程時(shí)間,延遲和曲線函數(shù)。(6)v-leave-to:定義離開過渡的結(jié)束狀態(tài)。在離開過渡被觸發(fā)之后下一幀生效(與此同時(shí)v-leave被刪除),在過渡/動(dòng)畫完成之后移除。
對于這些在過渡中切換的類名來說,如果使用不帶name屬性的<transition>,則“v-”將作為這些類名的默認(rèn)前綴。如果使用了<transitionname="my-transition"></transition>,那么v-enter會(huì)替換為my-transition-enter-from。v-enter-active和v-leave-active可以控制進(jìn)入/離開過渡的不同的緩和曲線。
過渡屬性與不透明度的關(guān)系圖6.1.1過渡的類名6.1.2CSS過渡
常用的過渡都是使用CSS過渡,同時(shí)可以設(shè)置持續(xù)時(shí)間和動(dòng)畫函數(shù)?!纠?-2】與【例6-1】有些類似,只是在使用CSS過渡時(shí)定義動(dòng)畫函數(shù)。該案例使用兩個(gè)transition標(biāo)記,一個(gè)帶有name屬性,一個(gè)不帶name屬性。帶name屬性的過渡標(biāo)記適用類樣式以”slide-fade-”開開頭,不帶name屬性的過渡標(biāo)記適用樣式以“v-”開頭。以下樣式同時(shí)定義了過渡時(shí)間函數(shù):.slide-fade-leave-active{transition:all.8scubic-bezier(1.0,0.5,0.8,1.0);}【例6-2】CSS過渡實(shí)戰(zhàn)
所謂動(dòng)畫就是讓一個(gè)元素從一個(gè)狀態(tài)逐漸向另一個(gè)狀態(tài)轉(zhuǎn)變的過程??梢栽谶@個(gè)過程中改變元素的CSS屬性。動(dòng)畫可以反復(fù)播放。CSS動(dòng)畫(CSSAnimations)用法同CSS過渡,區(qū)別是在動(dòng)畫中v-enter類名在節(jié)點(diǎn)插入DOM后不會(huì)立即刪除,而是在animationend事件觸發(fā)時(shí)刪除。6.1.3CSS動(dòng)畫【例6-3】CSS動(dòng)畫實(shí)戰(zhàn)。
第10行和第13行定義類名為“animation-enter-active(入場動(dòng)畫的時(shí)間段)”和“.animation-leave-active(離場動(dòng)畫的時(shí)間段)”的樣式,綁定動(dòng)畫myAnimations,并設(shè)置延時(shí)和反轉(zhuǎn)效果。
第17~21行定義關(guān)鍵幀,指定動(dòng)畫名稱為“myAnimations”,在其中定義3個(gè)過渡狀態(tài),分別0%、50%、100%,并設(shè)置轉(zhuǎn)換效果(縮放一定的倍數(shù))?!纠?-3】CSS動(dòng)畫實(shí)戰(zhàn)6.1.4自定義過渡的類名
可以通過以下屬性(attribute)來自定義過渡類名:enter-from-classenter-active-classenter-to-classleave-from-classleave-active-classleave-to-class
它們的優(yōu)先級高于普通的類名,這對于Vue的過渡系統(tǒng)和其他第三方CSS動(dòng)畫庫,例如animate.css(https://animate.style/)結(jié)合使用十分有用。
animate.css是一個(gè)來自國外的CSS3動(dòng)畫庫,它預(yù)設(shè)了抖動(dòng)(shake)、閃爍(flash)、翻轉(zhuǎn)(flip)、彈跳(bounce)、旋轉(zhuǎn)(rotateIn/rotateOut)、淡入淡出(fadeIn/fadeOut)等多達(dá)60多種動(dòng)畫效果,幾乎包含了所有常見的動(dòng)畫效果?!纠?-4】自定義過渡類名實(shí)戰(zhàn)
第10行定義了鏈接特定版本的外部樣式表文件“animate.css”。第23~25行給transition標(biāo)記定義name屬性,值為“custom-classes-transition”。并給該標(biāo)記添加自定義enter-active-class、leave-active-class屬性,其值分別為“animated
tada(晃動(dòng)效果)”、“animated
bounceOutRight(動(dòng)畫從右側(cè)彈跳)”6.1.5同時(shí)使用過渡和動(dòng)畫Vue通過設(shè)置相應(yīng)的事件監(jiān)聽器來了解過渡完成情況。可以是transitionend或animationend,這取決于給元素應(yīng)用的CSS規(guī)則。如果使用其中任何一種,Vue能自動(dòng)識別類型并設(shè)置監(jiān)聽。
但是,在一些場景中,可能需要給同一個(gè)元素同時(shí)設(shè)置兩種過渡動(dòng)效,比如animation很快的被觸發(fā)并完成了,而transition效果還沒結(jié)束。在這種情況中,就需要使用type屬性并設(shè)置animation或transition來明確聲明所需要Vue監(jiān)聽的類型。6.1.6顯性的過渡持續(xù)時(shí)間
在大多情況下,Vue可以自動(dòng)得出過渡效果的完成時(shí)機(jī)。默認(rèn)情況下,Vue會(huì)等待其在過渡效果的根元素的第一個(gè)transitionend或animationend事件。然而也可以不這樣設(shè)定,例如,可以精心編排的一系列過渡效果,其中一些嵌套的內(nèi)部元素相比于過渡效果的根元素有延遲的或更長的過渡效果。
在這種情況下,可以用<transition>組件上的duration
prop定制一個(gè)顯性的過渡持續(xù)時(shí)間(以毫秒計(jì)):<transition:duration="1000">...</transition>也可以定制進(jìn)入和移出的持續(xù)時(shí)間:<transition:duration="{enter:500,leave:800}">...</transition>【例6-5】同時(shí)使用過渡與動(dòng)畫和持續(xù)過渡時(shí)間實(shí)戰(zhàn)6.1.5同時(shí)使用過渡和動(dòng)畫6.1.7JavaScript鉤子可以在屬性中聲明JavaScript鉤子。參考代碼如下所示:注意:當(dāng)只用JavaScript過渡的時(shí)候,在enter和leave中必須使用done進(jìn)行回調(diào)。否則,它們將被同步調(diào)用,過渡會(huì)立即完成。推薦對于僅使用JavaScript過渡的元素添加v-bind:css="false",Vue會(huì)跳過CSS的檢測。這也可以避免過渡過程中CSS的影響。6.1.8Velocity動(dòng)畫庫簡介1.Velocity.js簡介Velocity是一個(gè)簡單易用、高性能、功能豐富的輕量級JS動(dòng)畫庫。它能和jQuery完美協(xié)作,并和$.animate()有相同的API,但它不依賴jQuery,可單獨(dú)使用。
Velocity不僅包含了$.animate()的全部功能,還擁有顏色動(dòng)畫、轉(zhuǎn)換動(dòng)畫(transforms)、循環(huán)、緩動(dòng)、SVG動(dòng)畫、和滾動(dòng)動(dòng)畫等特色功能。同時(shí)還支持duration、loop、delay、display等動(dòng)畫配置項(xiàng)的設(shè)置。
Velocity比$.animate()更快更流暢,性能甚至高于CSS3animation,是jQuery和CSS3transition的最佳組合,它支持所有現(xiàn)代瀏覽器。2.velocity的使用Velocity引入方法如下:<scriptsrc="/ajax/libs/velocity/1.5.0/velocity.min.js"></script>也可以將velocity.min.js文件下載到本地項(xiàng)目開發(fā)的公共子文件夾js中,供本地地調(diào)用。<scriptsrc="../js/velocity.min.js"></script>【基本語法】Velocity(element,{property:value},{option:optionvalue});【語法說明】element:表示DOM元素。{}:表示屬性值對,可以有多個(gè)屬性值對。要在同一個(gè)元素上鏈接另一個(gè)動(dòng)畫,只需在之前的velocity后再添加一個(gè)。Velocity(element1,{property:value},{option:optionValue});Velocity(element1,{property:value},{option:optionValue});【例6-6】JavaScript鉤子與velocity.js結(jié)合使用實(shí)戰(zhàn)。6.1.8Velocity動(dòng)畫庫簡介6.2初始渲染的過渡
可以通過appear屬性設(shè)置節(jié)點(diǎn)在初始渲染(出現(xiàn)時(shí))的過渡。這里默認(rèn)和進(jìn)入/離開過渡一樣,同樣也可以自定義CSS類名。標(biāo)記語法如下:<transition
appear
appear-class="custom-appear-class"
appear-to-class="custom-appear-to-class"
appear-active-class="custom-appear-active-class"
>
<!--
...
-->
</transition>
也可以自定義JavaScript鉤子。標(biāo)記語法如下:<transition
appear
v-on:before-appear="customBeforeAppearHook"
v-on:appear="customAppearHook"
v-on:after-appear="customAfterAppearHook"
v-on:appear-cancelled="customAppearCancelledHook"
>
<!--
...
-->
</transition>
在上面的例子中,無論是appear屬性,還是v-on:appear鉤子都會(huì)生成初始渲染過渡。6.3多個(gè)元素的過渡
最常見的多標(biāo)記過渡是一個(gè)列表和描述這個(gè)列表為空消息的元素。標(biāo)記語法如下:<transition>
<ul
v-if="items.length
>
0">
<!--
...
-->
</ul>
<p
v-else>對不起,沒有發(fā)現(xiàn)列表項(xiàng).</p>
</transition>
注意:當(dāng)有相同標(biāo)記名的元素切換時(shí),需要通過key屬性設(shè)置唯一的值來標(biāo)識,以讓Vue區(qū)分它們,否則Vue為了效率只會(huì)替換相同標(biāo)記內(nèi)部的內(nèi)容。即使在技術(shù)上沒有必要,給在<transition></transition>組件中的多個(gè)元素設(shè)置key是一個(gè)更好的實(shí)踐。
在一些場景中,也可以通過給同一個(gè)元素的key屬性設(shè)置不同的狀態(tài)來代替v-if和v-else。上面的例子可以改寫如下格式:<transition>
<button
v-bind:key="isEditing">
{{
isEditing
?
'保存'
:
'編輯'
}}
</button>
</transition>
6.3多個(gè)元素的過渡
使用多個(gè)v-if的多個(gè)元素的過渡可以重寫為綁定了動(dòng)態(tài)property的單個(gè)元素過渡。<transition>
<button
v-if="docState
===
'saved'"
key="saved">編輯</button>
<button
v-if="docState
===
'edited'"
key="edited">保存</button>
<button
v-if="docState
===
'editing'"
key="editing">取消</button>
</transition>
這種形式也可以重定義為如下格式:<!--HTML部分
-->
<transition>
<button
v-bind:key="docState">
{{
buttonMessage
}}
</button>
</transition>
…//JS部分
computed:
{
buttonMessage:
function
()
{
switch
(this.docState)
{
case
'saved':
return
'編輯'
case
'edited':
return
'保存'
case
'editing':
return
'取消'
}
}
}
在下列部分代碼中,在“on”按鈕和“off”按鈕的過渡中,兩個(gè)按鈕都被重繪了,一個(gè)離開過渡的時(shí)候,另一個(gè)開始進(jìn)入過渡。這是<transition></transition>的默認(rèn)行為(進(jìn)入和離開同時(shí)發(fā)生)。<transition
name="no-mode-fade">
<button
v-if="on"
key="on"
@click="on
=
false">on</button>
<button
v-else
key="off"
@click="on
=
true">off</button>
</transition>
<style>
.no-mode-fade-enter-active,
.no-mode-fade-leave-active
{transition:
opacity
.5s}
.no-mode-fade-enter,.no-mode-fade-leave-to
{opacity:
0}
</style>
Vue提供了過渡模式,通過mode屬性來設(shè)置,其值為“in-out/out-in”。其作用:in-out:新元素先進(jìn)行過渡,完成之后當(dāng)前元素過渡離開。out-in:當(dāng)前元素先進(jìn)行過渡,完成之后新元素過渡進(jìn)入。<transition
name="with-mode-fade"
mode="out-in">
<button
v-if="on"
key="on"
@click="on
=
false">
on
</button>
<button
v-else=""
key="off"
@click="on
=
true">
off
</button>
</transition>
其中in-out模式不經(jīng)常使用,但對于一些稍微不同的過渡效果還是很有用的。過渡模式-mode屬性【例6-7】多個(gè)元素的過渡綜合實(shí)戰(zhàn)【例6-7】多個(gè)元素的過渡綜合實(shí)戰(zhàn)-2【例6-7】多個(gè)元素的過渡綜合實(shí)戰(zhàn)-36.4多個(gè)組件的過渡
多個(gè)組件的過渡簡單很多,一般不需要使用key屬性。相反,可以只需要使用動(dòng)態(tài)組件。使用“內(nèi)置組件+v-bind:is”可以實(shí)現(xiàn)動(dòng)態(tài)組件?!净A(chǔ)語法】
<transition
name="component-fade"
mode="out-in">
<component
v-bind:is="display"></component>
</transition>
【語法說明】<component></component>元素是Vue里面的一個(gè)內(nèi)置組件。使用“is”屬性(需要通過v-bind給“is”綁定一個(gè)值)?!癷s”綁定的值(display)傳入一個(gè)組件名,就會(huì)切換到這個(gè)組件?!纠?-8】多組件過渡的實(shí)戰(zhàn)第55~57行定義動(dòng)態(tài)組件,使用component內(nèi)置組件并綁定is屬性(值為“display”)來動(dòng)態(tài)渲染組件。第23~31行定義過渡類樣式【例6-8】多組件過渡的實(shí)戰(zhàn)-2
6.5列表過渡
我們已經(jīng)熟悉了單個(gè)節(jié)點(diǎn)、同一時(shí)間渲染多個(gè)節(jié)點(diǎn)中的一個(gè)過渡/動(dòng)畫的方法。那么如果需要?jiǎng)討B(tài)渲染整個(gè)列表,例如使用v-for去遍歷所有的列表項(xiàng)呢?在這種場景中,不能使用<transition></transition>組件,需要使用<transition-group></transition-group>組件。
在深入案例之前,先了解一下關(guān)于這個(gè)組件的一些特點(diǎn):(1)不同于<transition></transition>,它會(huì)以一個(gè)真實(shí)元素呈現(xiàn),默認(rèn)為一個(gè)<span></span>??梢酝ㄟ^tag屬性更換為其他元素。代碼舉例如下:<transition-groupname="list"tag="p"><spanv-for="iteminitems"v-bind:key="item"class="list-item">{{item}}</span>
</transition-group>(2)過渡模式不可用,因?yàn)椴辉傧嗷デ袚Q特有的元素。(3)內(nèi)部元素總是需要提供唯一的key屬性值。(4)CSS過渡的類將會(huì)應(yīng)用在內(nèi)部的元素中,而不是這個(gè)組/容器本身。6.5.1列表的進(jìn)入/離開過渡
使用<transition-group></transition-group>來渲染列表,通過name屬性來定義過渡的CSS類名。其語法如下:<ul>
<transition-group
name="myList">
<li
v-for="(student,index)
in
students"
:key="">
{{index}}------{{}}------{{student.age}}
</li>
</transition-group>
</ul>
【例6-9】列表的進(jìn)入/離開過渡?!纠?-9】列表的進(jìn)入/離開過渡【例6-9】列表的進(jìn)入/離開過渡-2這是列表過渡初始效果這是列表成員增加時(shí)入場過渡效果這是列表成員離場過渡效果6.5.2列表的排序過渡<transition-group>組件不僅可以實(shí)現(xiàn)列表的進(jìn)入和離開動(dòng)畫,還可以改變定位。要使用這個(gè)新功能只需了解新增的類v-move,它會(huì)在元素的改變定位的過程中應(yīng)用。與之前的類名一樣,可以通過name屬性來自定義前綴,也可以通過move-class屬性來手動(dòng)設(shè)置。v-move對于設(shè)置過渡的切換時(shí)機(jī)和過渡曲線非常有用。需要借助于lodash.min.js來實(shí)現(xiàn)數(shù)組切換的各種效果。1.Lodash.js簡介
Loash.js是一個(gè)一致性、模塊化、高性能的JavaScript實(shí)用工具庫。通過降低array、number、objects、string等的使用難度,從而讓JavaSc
溫馨提示
- 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
- 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
- 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁內(nèi)容里面會(huì)有圖紙預(yù)覽,若沒有圖紙預(yù)覽就沒有圖紙。
- 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
- 5. 人人文庫網(wǎng)僅提供信息存儲(chǔ)空間,僅對用戶上傳內(nèi)容的表現(xiàn)方式做保護(hù)處理,對用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對任何下載內(nèi)容負(fù)責(zé)。
- 6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請與我們聯(lián)系,我們立即糾正。
- 7. 本站不保證下載資源的準(zhǔn)確性、安全性和完整性, 同時(shí)也不承擔(dān)用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。
最新文檔
- 2024年中職學(xué)校教案設(shè)計(jì)模板(共8篇)
- 馬術(shù)教學(xué)原則和課程設(shè)計(jì)
- 鐵藝護(hù)欄施工方案
- 2025年度藝術(shù)品收藏咨詢個(gè)人居間代理協(xié)議4篇
- 2024年學(xué)習(xí)加法教案
- 2024年心理咨詢師題庫及答案(名師系列)
- 遠(yuǎn)傳水表施工方案
- 香蕉催熟課程設(shè)計(jì)
- 鋼橋課程設(shè)計(jì)答案解析圖
- 2024礦業(yè)權(quán)交易居間合同
- 高中家長會(huì) 高二寒假線上家長會(huì)課件
- 違規(guī)行為與處罰管理制度
- 個(gè)人教師述職報(bào)告錦集10篇
- 四川省等八省2025年普通高中學(xué)業(yè)水平選擇性考試適應(yīng)性演練歷史試題(含答案)
- 《內(nèi)部培訓(xùn)師培訓(xùn)》課件
- 《雷達(dá)原理》課件-3.3.3教學(xué)課件:相控陣?yán)走_(dá)
- 西方史學(xué)史課件3教學(xué)
- 2024年中國醫(yī)藥研發(fā)藍(lán)皮書
- 紅色中國風(fēng)蛇年年會(huì)邀請函
- 廣東省佛山市 2023-2024學(xué)年五年級(上)期末數(shù)學(xué)試卷
- 2024年車輛修理合同范本
評論
0/150
提交評論