Skip to content

Commit

Permalink
test: basic animate group tests, trigger onEnter and onExit
Browse files Browse the repository at this point in the history
  • Loading branch information
Coltin Kifer committed Sep 8, 2024
1 parent c8bba64 commit c43629e
Show file tree
Hide file tree
Showing 5 changed files with 111 additions and 9 deletions.
2 changes: 1 addition & 1 deletion src/AnimateGroup.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ function AnimateGroup(props) {
appearOptions={appear}
enterOptions={enter}
leaveOptions={leave}
key={`child-${index}`} // eslint-disable-line
key={`child-${index}`} // eslint-disable-line
>
{child}
</AnimateGroupChild>
Expand Down
1 change: 1 addition & 0 deletions src/AnimateGroupChild.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -66,6 +66,7 @@ class AnimateGroupChild extends Component {
}

render() {
// eslint-disable-next-line @typescript-eslint/no-unused-vars
const { children, appearOptions, enterOptions, leaveOptions, ...props } = this.props;

return (
Expand Down
24 changes: 24 additions & 0 deletions test/AnimateGroup.spec.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -6,4 +6,28 @@ describe('AnimateGroup', () => {
it('Should render AnimateGroup', () => {
render(<AnimateGroup />);
});

it('Should render children wrapped in the default component span', () => {
const { container } = render(
<AnimateGroup>
<div></div>
<div></div>
</AnimateGroup>,
);

const isSpan = container.firstChild instanceof HTMLSpanElement;
expect(isSpan).toBe(true);
});

it('Should render children wrapped in provided component type div', () => {
const { container } = render(
<AnimateGroup component="div">
<div></div>
<div></div>
</AnimateGroup>,
);

const isDiv = container.firstChild instanceof HTMLDivElement;
expect(isDiv).toBe(true);
});
});
86 changes: 82 additions & 4 deletions test/AnimateGroupChild.spec.tsx
Original file line number Diff line number Diff line change
@@ -1,13 +1,91 @@
import React from 'react';
import { render } from '@testing-library/react';
import React, { useState } from 'react';
import { act, render, screen } from '@testing-library/react';
import AnimateGroupChild from '../src/AnimateGroupChild';

describe('AnimateGroupChild', () => {
it('Should render AnimateGroupChild', () => {
render(
it('Should render AnimateGroupChild and its children', () => {
const { container } = render(
<AnimateGroupChild>
<div />
</AnimateGroupChild>,
);

const isDiv = container.firstChild instanceof HTMLDivElement;
expect(isDiv).toBe(true);
});

it('Should render AnimateGroupChild with basic options set', () => {
const appearOptions = { duration: 0.5, steps: [] };
const leaveOptions = { duration: 0.5, steps: [{ duration: 0.2 }] };
const enterOptions = { duration: 0.5, steps: [{ duration: 0.2 }, { duration: 0.4 }] };
const { container } = render(
<AnimateGroupChild appearOptions={appearOptions} leaveOptions={leaveOptions} enterOptions={enterOptions}>
<div />
</AnimateGroupChild>,
);
});

const Example = ({ enterOptions, inPropDefault }) => {
const [inProp, setInProp] = useState(inPropDefault);

const appearOptions = { duration: 0.5, steps: [] };
const leaveOptions = { duration: 0.5, steps: [{ duration: 0.2, style: { opacity: 0 } }] };

return (
<>
<button type="button" onClick={() => setInProp(p => !p)}>
click me
</button>
<AnimateGroupChild
in={inProp}
appearOptions={appearOptions}
leaveOptions={leaveOptions}
enterOptions={enterOptions}
>
<div />
</AnimateGroupChild>
</>
);
};

it('Should render AnimateGroupChild and trigger enter state with custom onAnimationEnd', () => {
const enterOptions = {
duration: 0.5,
steps: [
{ duration: 0.2, style: { opacity: 10 } },
{ duration: 0.4, style: { opacity: 10 } },
],
onAnimationEnd: vi.fn(),
};

render(<Example enterOptions={enterOptions} inPropDefault={false} />);
// enter state triggered
act(() => {
screen.getByText('click me').click();
});
});

it('Should render AnimateGroupChild and trigger enter state without custom onAnimationEnd', () => {
const enterOptions = {
duration: 0.5,
steps: [
{ duration: 0.2, style: { opacity: 10 } },
{ duration: 0.4, style: { opacity: 10 } },
],
};
render(<Example enterOptions={enterOptions} inPropDefault={false} />);
// enter state triggered
act(() => {
screen.getByText('click me').click();
});
});

it('Should render AnimateGroupChild and trigger exit state', () => {
const enterOptions = { duration: 0.5, steps: [{ duration: 0.2, style: { opacity: 0 } }, { duration: 0.4 }] };
render(<Example enterOptions={enterOptions} inPropDefault={true} />);
// enter state triggered
act(() => {
screen.getByText('click me').click();
});
});
});
7 changes: 3 additions & 4 deletions test/configUpdate.spec.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,5 @@
import * as util from '../src/util';
import animationFunction, { alpha } from '../src/configUpdate';
import { configEasing } from '../src/easing';
import { waitFor } from '@testing-library/react';

let requestAnimationFrameMock;
let cancelAnimationFrameMock;
Expand Down Expand Up @@ -65,10 +63,10 @@ describe('animationFunction', () => {
});

it('should use timingUpdate if easing.isStepper is false', () => {
easing = vi.fn(() => vi.fn());
easing = configEasing('spring');
const from = { x: 0, y: 0 };
const to = { x: 100, y: 100 };
const duration = 1;
const duration = 20;

const startAnimation = animationFunction(from, to, easing, duration, render);
startAnimation();
Expand Down Expand Up @@ -102,6 +100,7 @@ describe('animationFunction', () => {

startAnimation();
vi.advanceTimersToNextFrame();
vi.runAllTimers();

expect(render).toHaveBeenCalledWith({
x: from.x,
Expand Down

0 comments on commit c43629e

Please sign in to comment.