angular的生命周期

1、編譯階段

第一個(gè)階段是編譯階段。在編譯階段,AngularJS會(huì)遍歷整個(gè)HTML文檔并根據(jù)JavaScript中的指令定義來處理頁面上聲明的指令。

一旦對指令和其中的子模板進(jìn)行遍歷或編譯,編譯后的模板會(huì)返回一個(gè)叫做模板函數(shù)的函數(shù)。我們有機(jī)會(huì)在指令的模板函數(shù)被返回前,對編譯后的DOM樹進(jìn)行修改。

在這個(gè)時(shí)間點(diǎn)DOM樹還沒有進(jìn)行數(shù)據(jù)綁定,意味著如果此時(shí)對DOM樹進(jìn)行操作只會(huì)有很少的性能開銷?;诖它c(diǎn), ng-repeat和ng-transclude等內(nèi)置指令會(huì)在這個(gè)時(shí)候,也就是還未與任何作用域數(shù)據(jù)進(jìn)行綁定時(shí)對DOM進(jìn)行操作。

2、compile(對象或函數(shù))

compile選項(xiàng)可以返回一個(gè)對象或函數(shù)。

compile選項(xiàng)本身并不會(huì)被頻繁使用,但是link函數(shù)則會(huì)被經(jīng)常使用。本質(zhì)上,當(dāng)我們設(shè)置了link選項(xiàng),實(shí)際上是創(chuàng)建了一個(gè)postLink()鏈接函數(shù),以便compile()函數(shù)可以定義鏈接函數(shù)。

通常情況下,如果設(shè)置了compile函數(shù),說明我們希望在指令和實(shí)時(shí)數(shù)據(jù)被放到DOM中之前進(jìn)行DOM操作,在這個(gè)函數(shù)中進(jìn)行諸如添加和刪除節(jié)點(diǎn)等DOM操作是安全的。

注:compile和link選項(xiàng)是互斥的。如果同時(shí)設(shè)置了這兩個(gè)選項(xiàng),那么會(huì)把compile所返回的函數(shù)當(dāng)作鏈接函數(shù),而link選項(xiàng)本身則會(huì)被忽略。

不要進(jìn)行DOM事件監(jiān)聽器的注冊:這個(gè)操作應(yīng)該在鏈接函數(shù)中完成。

compile: function(tEle, tAttrs, transcludeFn) {

var tplEl = angular.element('

' +'

' +'
');

var h2 = tplEl.find('h2');

h2.attr('type', tAttrs.type);

h2.attr('ng-model', tAttrs.ngModel);

h2.val("hello");

tEle.replaceWith(tplEl);

return function(scope, ele, attrs) {

// 連接函數(shù)

};

}

編譯函數(shù)負(fù)責(zé)對模板DOM進(jìn)行轉(zhuǎn)換。

鏈接函數(shù)負(fù)責(zé)將作用域和DOM進(jìn)行鏈接。

3、鏈接

用link函數(shù)創(chuàng)建可以操作DOM的指令。

鏈接函數(shù)是可選的。如果定義了編譯函數(shù),它會(huì)返回鏈接函數(shù),因此當(dāng)兩個(gè)函數(shù)都定義了時(shí),編譯函數(shù)會(huì)重載鏈接函數(shù)。如果我們的指令很簡單,并且不需要額外的設(shè)置,可以從工廠函數(shù) (回

調(diào)函數(shù))返回一個(gè)函數(shù)來代替對象。如果這樣做了,這個(gè)函數(shù)就是鏈接函數(shù)。

下面兩種定義指令的方式在功能上是完全一樣的:

angular.module('myApp', [])

.directive('myDirective', function() {

return {

pre: function(tElement, tAttrs, transclude) {

// 在子元素被鏈接之前執(zhí)行

// 在這里進(jìn)行Don轉(zhuǎn)換不安全

// 之后調(diào)用'lihk'h函數(shù)將無法定位要鏈接的元素

},

post: function(scope, iElement, iAttrs, controller) {

// 在子元素被鏈接之后執(zhí)行

// 如果在這里省略掉編譯選項(xiàng)

//在這里執(zhí)行DOM轉(zhuǎn)換和鏈接函數(shù)一樣安全嗎

}

};

});

angular.module('myApp', [])

.directive('myDirective', function() {

return {

link: function(scope, ele, attrs) {

return {

pre: function(tElement, tAttrs, transclude) {

// 在子元素被鏈接之前執(zhí)行

// 在這里進(jìn)行Don轉(zhuǎn)換不安全

// 之后調(diào)用'lihk'h函數(shù)將無法定位要鏈接的元素

},

post: function(scope, iElement, iAttrs, controller) {

// 在子元素被鏈接之后執(zhí)行

// 如果在這里省略掉編譯選項(xiàng)

//在這里執(zhí)行DOM轉(zhuǎn)換和鏈接函數(shù)一樣安全嗎

}

}

}

});

下面看一下鏈接函數(shù)中的參數(shù):

scope

指令用來在其內(nèi)部注冊監(jiān)聽器的作用域。

iElement

iElement參數(shù)代表實(shí)例元素,指使用此指令的元素。在postLink函數(shù)中我們應(yīng)該只操作此元素的子元素,因?yàn)樽釉匾呀?jīng)被鏈接過了。

iAttrs

iAttrs參數(shù)代表實(shí)例屬性,是一個(gè)由定義在元素上的屬性組成的標(biāo)準(zhǔn)化列表,可以在所有指令的鏈接函數(shù)間共享。會(huì)以javascript對象的形式進(jìn)行傳遞。

controller

controller參數(shù)指向require選項(xiàng)定義的控制器。如果沒有設(shè)置 require選項(xiàng) ,那么controller參數(shù)的值為undefined。

控制器在所有的指令間共享,因此指令可以將控制器當(dāng)作通信通道(公共API)。如果設(shè)置了多個(gè)require,那么這個(gè)參數(shù)會(huì)是一個(gè)由控制器實(shí)例組成的數(shù)組,而不只是一個(gè)單獨(dú)的控制器。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請結(jié)合常識與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容