Angular中定义了很多内部指令,显著标志就是以ng-XXX开头,但有的时候为了实现特定的功能,只使用内部指令是远远不能满足我们需求的,这时候自定义指令就显得尤为重要
内部指令就不多说了,下面是关于自定义指令需要注意的地方,有不对的地方欢迎指正。
举个自定义指令写法的栗子:
angular.module('myApp', [])
.directive('myDirective',function(){
return {
restrict:'E',
template:'<button>点击</button>'
}
})
讲解栗子:
- 我们可以直接使用Angular中的
directive()
这个方法定义了一个新的指令 - 参数1,是指令名称,上面定义了一个my-directive的指令
- 参数2,是对参数1也就是刚刚自定义指令的说明,可以直接是一个
function(){//相应的代码}
,也可以是一个函数名
,但这个函数需要在下面定义,推荐第二种写法; - 参数2返回的是参数1这个指令对应的对象,它包括以下几点:
restrict[string]这个属性,主要是用来规定指令在HTML代码中可以使用什么表现形式。
- E代表元素(element)
- A代表属性(attribute)
- C代表类(class)
- M代表注释(common)
推荐项目中使用EA这两种写法,一般我们也就使用EA比较多。
- E---> 作为一个HTML元素来使用
<my-directive></my-directive>或者<my-directive/>
- A ----> 作为元素的属性来使用
<div my-directive></div>
- C--->作为一个元素的类来使用
<div class="my-directive"></div>
- M---> 作为注释来使用
需要注意的是:
- 使用注释这种方式有个很隐秘的坑,比如:
directive: my-directive
这个的后面要有一个空格,切记,不然写了也是白写; -
不推荐
使用这种写法,一般项目也不使用注释这种方式;
template[string or function]这个属性,规定了指令被Angular编译和链接(link)后生成的HTML标记,这个属性可以简单到只有一个HTML文本在里面,也可以特别复杂,当该属性的值为function的时候,那么该方法返回的就是代表模板的字符串,同时也可以在里面使用{{}}这个表达式。
但是在一般情况下,template这个属性都会被templateUrl取代掉,用它来指向一个外部的文件地址,所以我们通常把模板放在外部的一个HTML文件中,然后使用templateUrl来指向他。
priority[number]属性,这个属性是来规定自定义的指令的优先级的
当一个DOM元素上面有一个以上的指令的时候,就需要去比较指令的优先级了,优先级高的指令先执行。这个优先级就是用来在执行指令的compile函数前,先排序的
terminal[boolean]属性,该参数用来定义是否停止当前元素上比本指令优先级低的指令
如果值为true,就是正常情况,按照优先级高低的顺序来执行,如果设置为false,就不会执行当前元素上比本指令优先级低的指令。
replace[boolean]属性,这个属性用来规定生成的HTML内容是否会替换掉定义此指令的HTML元素。
当我们把该属性的值设为true的时候,打开控制台看看你会发现这个指令生成的元素会是这样的:
<button>点击</button>
当值为false时为:
<my-directive>
<button>点击</button>
</my-directive>
link[function]属性,在上面的例子中,我们自定义的指令其实没有多大意义,这只是一个最简单的指令,有好多的属性我们都没有为他定义,所以没有多大用途。
比如这个link函数,它包括三个参数:scope、element、attrs。这个link函数主要是用来添加对DOM元素的事件监听、监视模型属性变化、以及更新DOM的。它里面三个参数:
scope参数,在我们没有为指令定义scope属性的时候,那么他代表的就是父controller的scope。
element参数,就是指令的jQLite(jQuery的子集)包装DOM元素。如果你在引入AngularJS之前引入了jQuery,那么这个元素就是jQuery元素,而不是jQLite元素。由于这个元素已经被jQuery/jQLite包装了,所以我们就在进行DOM操作的时候就不需要再使用 $()来进行包装。
attrs参数,它包含了该指令所在元素的属性的标准化参数对象。