mirror of
https://github.com/ionic-team/ionic-framework.git
synced 2026-03-13 10:22:08 +08:00
add base before and after methods, add tests
This commit is contained in:
@@ -56,6 +56,24 @@ const generateKeyframeString = (name: string | undefined, keyframes: any[] = [])
|
||||
return keyframeString.join(' ');
|
||||
};
|
||||
|
||||
const createKeyframeStylesheet = (keyframeString: string): HTMLElement => {
|
||||
const stylesheet = document.createElement('style');
|
||||
stylesheet.appendChild(document.createTextNode(keyframeString));
|
||||
document.querySelector('head')!.appendChild(stylesheet);
|
||||
|
||||
return stylesheet;
|
||||
};
|
||||
|
||||
const addClassToArray = (classes: string[] = [], className: string | string[] | undefined): string[] => {
|
||||
if (className !== undefined) {
|
||||
const classNameToAppend = (Array.isArray(className)) ? className : [className];
|
||||
|
||||
return [...classes, ...classNameToAppend];
|
||||
}
|
||||
|
||||
return classes;
|
||||
};
|
||||
|
||||
export class Animation {
|
||||
private elements: Element[] = [];
|
||||
private childAnimations: Animation[] = [];
|
||||
@@ -74,32 +92,138 @@ export class Animation {
|
||||
|
||||
parentAnimation: Animation | undefined;
|
||||
|
||||
private beforeAddClasses: string[] = [];
|
||||
private beforeRemoveClasses: string[] = [];
|
||||
private beforeStylesValue: { [property: string]: any } = {};
|
||||
|
||||
private afterAddClasses: string[] = [];
|
||||
private afterRemoveClasses: string[] = [];
|
||||
private afterStylesValue: { [property: string]: any } = {};
|
||||
|
||||
constructor(public _name: string | undefined) {}
|
||||
|
||||
/**
|
||||
* Destroy this animation and all child animations.
|
||||
*/
|
||||
destroy(): Animation {
|
||||
this.childAnimations.forEach(childAnimation => {
|
||||
childAnimation.destroy();
|
||||
});
|
||||
|
||||
this.elements = [];
|
||||
this.childAnimations = [];
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Add CSS class to this animation's elements
|
||||
* before the animation begins.
|
||||
*/
|
||||
beforeAddClass(className: string | string[] | undefined): Animation {
|
||||
this.beforeAddClasses = addClassToArray(this.beforeAddClasses, className);
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Remove CSS class from this animation's elements
|
||||
* before the animation begins.
|
||||
*/
|
||||
beforeRemoveClass(className: string | string[] | undefined): Animation {
|
||||
this.beforeRemoveClasses = addClassToArray(this.beforeRemoveClasses, className);
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set CSS inline styles to this animation's elements
|
||||
* before the animation begins.
|
||||
*/
|
||||
beforeStyles(styles: { [property: string]: any } = {}): Animation {
|
||||
this.beforeStylesValue = styles;
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Clear CSS inline styles from this animation's elements
|
||||
* before the animation begins.
|
||||
*/
|
||||
beforeClearStyles(propertyNames: string[] = []): Animation {
|
||||
for (const property of propertyNames) {
|
||||
this.beforeStylesValue[property] = '';
|
||||
}
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Add CSS class to this animation's elements
|
||||
* after the animation ends.
|
||||
*/
|
||||
afterAddClass(className: string | string[] | undefined): Animation {
|
||||
this.afterAddClasses = addClassToArray(this.afterAddClasses, className);
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Remove CSS class from this animation's elements
|
||||
* after the animation ends.
|
||||
*/
|
||||
afterRemoveClass(className: string | string[] | undefined): Animation {
|
||||
this.afterRemoveClasses = addClassToArray(this.afterRemoveClasses, className);
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set CSS inline styles to this animation's elements
|
||||
* after the animation ends.
|
||||
*/
|
||||
afterStyles(styles: { [property: string]: any } = {}): Animation {
|
||||
this.afterStylesValue = styles;
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Clear CSS inline styles from this animation's elements
|
||||
* after the animation ends.
|
||||
*/
|
||||
afterClearStyles(propertyNames: string[] = []): Animation {
|
||||
for (const property of propertyNames) {
|
||||
this.afterStylesValue[property] = '';
|
||||
}
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
getEasing(): string | undefined {
|
||||
if (this._easing !== undefined) { return this._easing; }
|
||||
if (this.parentAnimation && this.parentAnimation.getEasing() !== undefined) { return this.parentAnimation.getEasing(); }
|
||||
if (this.parentAnimation) { return this.parentAnimation.getEasing(); }
|
||||
|
||||
return undefined;
|
||||
}
|
||||
|
||||
getDuration(): number | undefined {
|
||||
if (this._duration !== undefined) { return this._duration; }
|
||||
if (this.parentAnimation && this.parentAnimation.getDuration() !== undefined) { return this.parentAnimation.getDuration(); }
|
||||
if (this.parentAnimation) { return this.parentAnimation.getDuration(); }
|
||||
|
||||
return undefined;
|
||||
}
|
||||
|
||||
getIterations(): number | undefined {
|
||||
if (this._iterations !== undefined) { return this._iterations; }
|
||||
if (this.parentAnimation && this.parentAnimation.getIterations() !== undefined) { return this.parentAnimation.getIterations(); }
|
||||
if (this.parentAnimation) { return this.parentAnimation.getIterations(); }
|
||||
|
||||
return undefined;
|
||||
}
|
||||
|
||||
getDelay(): number | undefined {
|
||||
if (this._delay !== undefined) { return this._delay; }
|
||||
if (this.parentAnimation && this.parentAnimation.getDelay() !== undefined) { return this.parentAnimation.getDelay(); }
|
||||
if (this.parentAnimation) { return this.parentAnimation.getDelay(); }
|
||||
|
||||
return undefined;
|
||||
}
|
||||
@@ -165,12 +289,7 @@ export class Animation {
|
||||
|
||||
private initializeAnimation(): void {
|
||||
if (!this.stylesheet) {
|
||||
const stylesheet = document.createElement('style');
|
||||
stylesheet.appendChild(document.createTextNode(this._keyframeString));
|
||||
|
||||
document.querySelector('head')!.appendChild(stylesheet);
|
||||
|
||||
this.stylesheet = stylesheet;
|
||||
this.stylesheet = createKeyframeStylesheet(this._keyframeString);
|
||||
}
|
||||
|
||||
const animationName = this._name;
|
||||
@@ -227,18 +346,16 @@ export class Animation {
|
||||
}
|
||||
|
||||
pause(): Animation {
|
||||
if (!this.initialized) {
|
||||
this.initializeAnimation();
|
||||
if (this.initialized) {
|
||||
this.childAnimations.forEach(animation => {
|
||||
animation.pause();
|
||||
});
|
||||
|
||||
this.elements.forEach(element => {
|
||||
(element as HTMLElement).style.animationPlayState = 'paused';
|
||||
});
|
||||
}
|
||||
|
||||
this.childAnimations.forEach(animation => {
|
||||
animation.pause();
|
||||
});
|
||||
|
||||
this.elements.forEach(element => {
|
||||
(element as HTMLElement).style.animationPlayState = 'paused';
|
||||
});
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
|
||||
@@ -123,6 +123,83 @@ describe('Animation Class', () => {
|
||||
});
|
||||
});
|
||||
|
||||
describe('Before and After Animation Methods', () => {
|
||||
let animation;
|
||||
beforeEach(() => {
|
||||
animation = new Animation();
|
||||
});
|
||||
|
||||
it('should register all "before" styles', () => {
|
||||
animation.beforeStyles({ 'background': 'red', 'opacity': 1 });
|
||||
expect(Object.keys(animation.beforeStylesValue).length).toEqual(2);
|
||||
});
|
||||
|
||||
it('should register all "before" classes given arrays', () => {
|
||||
const classesToAdd = ['my-class', 'hello-world'];
|
||||
const classesToRemove = ['ionic-framework'];
|
||||
|
||||
animation.beforeAddClass(classesToAdd);
|
||||
animation.beforeRemoveClass(classesToRemove);
|
||||
|
||||
expect(animation.beforeAddClasses.length).toEqual(classesToAdd.length);
|
||||
expect(animation.beforeRemoveClasses.length).toEqual(classesToRemove.length);
|
||||
});
|
||||
|
||||
it('should register all "before" classes given strings', () => {
|
||||
const classesToAdd = 'my-class';
|
||||
const classesToRemove = 'ionic-framework';
|
||||
|
||||
animation.beforeAddClass(classesToAdd);
|
||||
animation.beforeRemoveClass(classesToRemove);
|
||||
|
||||
expect(animation.beforeAddClasses.length).toEqual(1);
|
||||
expect(animation.beforeRemoveClasses.length).toEqual(1);
|
||||
});
|
||||
|
||||
it('should not register "before" classes given undefined', () => {
|
||||
animation.beforeAddClass(undefined);
|
||||
animation.beforeRemoveClass(undefined);
|
||||
|
||||
expect(animation.beforeAddClasses.length).toEqual(0);
|
||||
expect(animation.beforeRemoveClasses.length).toEqual(0);
|
||||
});
|
||||
|
||||
it('should register all "after" styles', () => {
|
||||
animation.afterStyles({ 'background': 'red', 'opacity': 1 });
|
||||
expect(Object.keys(animation.afterStylesValue).length).toEqual(2);
|
||||
});
|
||||
|
||||
it('should register all "after" classes given arrays', () => {
|
||||
const classesToAdd = ['my-class', 'hello-world'];
|
||||
const classesToRemove = ['ionic-framework'];
|
||||
|
||||
animation.afterAddClass(classesToAdd);
|
||||
animation.afterRemoveClass(classesToRemove);
|
||||
|
||||
expect(animation.afterAddClasses.length).toEqual(classesToAdd.length);
|
||||
expect(animation.afterRemoveClasses.length).toEqual(classesToRemove.length);
|
||||
});
|
||||
|
||||
it('should register all "after" classes given strings', () => {
|
||||
const classesToAdd = 'my-class';
|
||||
const classesToRemove = 'ionic-framework';
|
||||
|
||||
animation.afterAddClass(classesToAdd);
|
||||
animation.afterRemoveClass(classesToRemove);
|
||||
|
||||
expect(animation.afterAddClasses.length).toEqual(1);
|
||||
expect(animation.afterRemoveClasses.length).toEqual(1);
|
||||
});
|
||||
|
||||
it('should not register "after" classes given undefined', () => {
|
||||
animation.afterAddClass(undefined);
|
||||
animation.afterRemoveClass(undefined);
|
||||
|
||||
expect(animation.afterAddClasses.length).toEqual(0);
|
||||
expect(animation.afterRemoveClasses.length).toEqual(0);
|
||||
});
|
||||
});
|
||||
|
||||
describe('Animation Config Methods', () => {
|
||||
let animation;
|
||||
beforeEach(() => {
|
||||
|
||||
@@ -13,7 +13,7 @@
|
||||
<script type="module" src="../../../../../dist/ionic/ionic.esm.js"></script>
|
||||
<script type="module">
|
||||
import { Animation as IonicAnimation } from '../../../../dist/collection/utils/animation/animation.js';
|
||||
import { createGesture } from '../../../../dist/esm/index-0303391f.js';
|
||||
import { createGesture } from '../../../../dist/ionic/index-a098653b.js';
|
||||
|
||||
window.IonicAnimation = IonicAnimation;
|
||||
|
||||
|
||||
Reference in New Issue
Block a user