I am trying to implement a countdown timer using angular as implemented in this
The problem is that the animations are not being applied on change of values, what I am I missing?
html
<div>
<div class="flipclock" *ngIf="timer$ | async as timer">
<div id="container" class="flipclock">
<ul class="flip " *ngFor="let time of timer">
<li
*ngFor="let item of time.split(''); let i = index"
[class.d1]="i === 1"
[class.d2]="i === 0"
>
<section class="ready">
<div class="up">
<div class="shadow"></div>
<div class="inn">{{ item }}</div>
</div>
<div class="down">
<div class="shadow"></div>
<div class="inn">{{ item }}</div>
</div>
</section>
<section class="active">
<div class="up">
<div class="shadow"></div>
<div class="inn">{{ item }}</div>
</div>
<div class="down">
<div class="shadow"></div>
<div class="inn">{{ item }}</div>
</div>
</section>
</li>
</ul>
</div>
</div>
</div>
export class AppComponent {
name = 'Angular ' + VERSION.major;
initialMinutes$ = new BehaviorSubject(30);
expired$ = new Subject();
@Input()
set minutes(val) {
this.initialMinutes$.next(val);
}
timer$ = this.initialMinutes$.pipe(
switchMap(minutes => timer(0, 1000).pipe(
map(t => minutes * 60 - t),
tap(seconds => {
if (seconds < 0) {
this.expired$.next();
}
}),
takeUntil(this.expired$),
map(seconds => ({
hr: Math.max(Math.floor(seconds / 3600), 0),
min: Math.max(Math.floor((seconds % 3600) / 60), 0),
s: (seconds % 60)
})),
map(({hr, min, s}) => ([
hr > 9 ? hr.toString() : '0' + hr.toString(),
min > 9 ? min.toString() : '0' + min.toString(),
s > 9 ? s.toString() : '0' + s.toString(),
]))
))
);
}
css
.flipclock {
}
.flipclock hr {
position: absolute;
left: 0;
top: 65px;
width: 100%;
height: 3px;
border: 0;
background: #000;
z-index: 10;
opacity: 0;
}
ul.flip {
position: relative;
float: left;
margin: 10px;
padding: 0;
width: 90px;
height: 60px;
font-size: 60px;
font-weight: 400;
line-height: 60px;
}
ul.flip li {
float: left;
margin: 0;
padding: 0;
width: 49%;
height: 100%;
-webkit-perspective: 200px;
list-style: none;
}
ul.flip li.d1 {
float: right;
}
ul.flip li section {
z-index: 1;
position: absolute;
left: 0;
top: 0;
width: 100%;
height: 100%;
}
ul.flip li section:first-child {
z-index: 2;
}
ul.flip li div {
z-index: 1;
position: absolute;
left: 0;
width: 100%;
height: 49%;
overflow: hidden;
}
ul.flip li div .shadow {
display: block;
position: absolute;
width: 100%;
height: 100%;
z-index: 2;
}
ul.flip li div.up {
-webkit-transform-origin: 50% 100%;
top: 0;
}
ul.flip li div.down {
-webkit-transform-origin: 50% 0;
bottom: 0;
}
ul.flip li div div.inn {
position: absolute;
left: 0;
z-index: 1;
width: 100%;
height: 200%;
color: #fff;
text-shadow: 0 0 2px #fff;
text-align: center;
background-color: #000;
border-radius: 6px;
}
ul.flip li div.up div.inn {
top: 0;
}
ul.flip li div.down div.inn {
bottom: 0;
}
/*--------------------------------------
PLAY
--------------------------------------*/
.play ul section.ready {
z-index: 3;
}
.play ul section.active {
-webkit-animation: index .5s .5s linear both;
z-index: 2;
}
@-webkit-keyframes index {
0% {
z-index: 2;
}
5% {
z-index: 4;
}
100% {
z-index: 4;
}
}
.play ul section.active .down {
z-index: 2;
-webkit-animation: flipdown .5s .5s linear both;
}
@-webkit-keyframes flipdown {
0% {
-webkit-transform: rotateX(90deg);
}
80% {
-webkit-transform: rotateX(5deg);
}
90% {
-webkit-transform: rotateX(15deg);
}
100% {
-webkit-transform: rotateX(0deg);
}
}
.play ul section.ready .up {
z-index: 2;
-webkit-animation: flipup .5s linear both;
}
@-webkit-keyframes flipup {
0% {
-webkit-transform: rotateX(0deg);
}
90% {
-webkit-transform: rotateX(0deg);
}
100% {
-webkit-transform: rotateX(-90deg);
}
}
/*--------------------------------------
SHADOW
--------------------------------------*/
.play ul section.ready .up .shadow {
background: -webkit-gradient(linear, left top, left bottom, color-stop(0%, rgba(0, 0, 0, .1)), color-stop(100%, rgba(0, 0, 0, 1)));
background: linear-gradient(to bottom, rgba(0, 0, 0, .1) 0%, rgba(0, 0, 0, 1) 100%);
-webkit-animation: show .5s linear both;
}
.play ul section.active .up .shadow {
background: -webkit-gradient(linear, left top, left bottom, color-stop(0%, rgba(0, 0, 0, .1)), color-stop(100%, rgba(0, 0, 0, 1)));
background: linear-gradient(to bottom, rgba(0, 0, 0, .1) 0%, rgba(0, 0, 0, 1) 100%);
-webkit-animation: hide .5s .3s linear both;
}
/*DOWN*/
.play ul section.ready .down .shadow {
background: -webkit-gradient(linear, left top, left bottom, color-stop(0%, rgba(0, 0, 0, 1)), color-stop(100%, rgba(0, 0, 0, .1)));
background: linear-gradient(to bottom, rgba(0, 0, 0, 1) 0%, rgba(0, 0, 0, .1) 100%);
-webkit-animation: show .5s linear both;
}
.play ul section.active .down .shadow {
background: -webkit-gradient(linear, left top, left bottom, color-stop(0%, rgba(0, 0, 0, 1)), color-stop(100%, rgba(0, 0, 0, .1)));
background: linear-gradient(to bottom, rgba(0, 0, 0, 1) 0%, rgba(0, 0, 0, .1) 100%);
-webkit-animation: hide .5s .3s linear both;
}
@-webkit-keyframes show {
0% {
opacity: 0;
}
90% {
opacity: .10;
}
100% {
opacity: 1;
}
}
@-webkit-keyframes hide {
0% {
opacity: 1;
}
80% {
opacity: .20;
}
100% {
opacity: 0;
}
}
Edit 1
I have managed to get animations to reflect but it is now reflecting on all the items