The ngAnimate on angular(1.2.13)

angular的ngAnimate主要是依照不同的Directive,對照不同的class做切換,以下有一張官方提供的對照表:

Directive Supported Animations
ngRepeat enter,leave and move
ngView enter and leave
ngInclude enter and leave
ngSwitch enter and leave
ngIf enter and leave
ngClass add and remove
ngShow & ngHide add and remove (the ng-hide class value)

比較值得注意的是,angular(1.2)以上的版本,是依據directive的目前的status,替換不同的class,它會在每個不同的status加上ng-....的class,如ng-enterng-leave等的。

ngRepeat為例,定義一個html結構:

1
2
3
4
5
<ul>
<li ng-repeat="role in roles" class="demo">
{{role}}
</li>
</ul>

加入一個值到roles

1
$scope.roles.push( "programer" );

則此時會先插入一個ng-enterclass,做初始配置用,接著在插入ng-enter-active的class,改變後的狀態,只有設定transition,這時就會產生動畫效果。

依照element的class名稱,css的配置如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
.demo.ng-enter {

-webkit-transition: all 1s linear;
transition: all 1s linear;

/**
* set styles
*/

}
.demo.ng-enter-active {
/**
* set styles
*/

}

若是不支援css3的瀏覽器,則必須自己實作動畫效果:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
app.animation('.demo', function() {

return {

enter:function( element, done ){

doEffect( done );

return function( cancelled ) {

if ( cancelled ) {

//stopEffect();

} else {

//completeTheAnimation();
}

};
}

};

});

如果要使用到jquery來做特效,需在angular載入之前,先行載入jquery,因為angular會判斷要使用jqueryjqlite,然後再做一些處理。若要使用jquery改變顏色,則需要額外載入jquery-color。另外如果同時用javascript和css實作特效,則css特效會被javascript所覆蓋。

Example

Install

1
bower install angular angular-animate jquery jquery-color

Create a angular app and load a ngAnimate module( app.js ):

1
var app = angular.module('angularNgApp', ["ngAnimate"]);

html:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<link rel="stylesheet" href="main.css">
</head>
<body ng-app="angularNgApp">

<div ng-controller="MainCtrl">
<ul>
<li ng-repeat="thing in awesomeThings" class="demo">
{{thing}}
</li>
</ul>
</div>

<!--[if lt IE 9]>
<script src="bower_components/es5-shim/es5-shim.js"></script>
<script src="bower_components/json3/lib/json3.min.js"></script>
<![endif]-->



<!-- bower:js -->
<script src="bower_components/jquery/dist/jquery.js"></script>
<script src="bower_components/jquery-color/jquery.color.js"></script>
<script src="bower_components/angular/angular.js"></script>
<script src="bower_components/angular-animate/angular-animate.js"></script>
<!-- endbower -->

<script src="app.js"></script>
<script src="controller.js"></script>
<!--[if lt IE 9]>
<script src="animation.js"></script>
<![endif]-->


</body>
</html>

main.css:

1
2
3
4
5
6
7
8
9
10
.demo.ng-enter {

-webkit-transition: all 1s linear;
transition: all 1s linear;
background: #000;
}

.demo.ng-enter-active {
background: #fc3;
}

controller.js:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
app.controller('MainCtrl', function ( $scope, $timeout ) {

$scope.awesomeThings = [
'HTML5 Boilerplate',
'AngularJS',
'Karma'
];

$timeout( function(){

$scope.awesomeThings.push("123");

}, 2200);

});

animation.js:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
app.animation('.demo', function() {

return {
enter : function( element, done ) {

element.animate({
'background-color': 'red'
}, done);

return function( cancelled ) {

if(cancelled) {
//stopTheAnimation();
}
else {
//completeTheAnimation();
}
}
}
};
});