Skip to content

Commit

Permalink
tests: first test files (#9)
Browse files Browse the repository at this point in the history
  • Loading branch information
yhattav authored Nov 15, 2024
1 parent 9518e39 commit 107ebd5
Show file tree
Hide file tree
Showing 10 changed files with 216 additions and 17 deletions.
1 change: 0 additions & 1 deletion example/src/components/GravityPoint/GravityPoint.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -56,7 +56,6 @@ export const GravityPointComponent: React.FC<GravityPointComponentProps> = ({
<motion.div
ref={elementRef}
onUpdate={(latest) => {
console.log('LATEST', latest);
reportPosition({ x: Number(latest.x), y: Number(latest.y) });
}}
drag
Expand Down
11 changes: 5 additions & 6 deletions example/src/components/GravitySimulator/GravitySimulator.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -87,15 +87,13 @@ export const GravitySimulator: React.FC<GravitySimulatorProps> = ({
}, []);

const handleDrag = throttle(() => {
console.log('handleDrag');
setTimeout(() => {
setIsDragging(true);
}, 0);
});

const handleReportNewPosition = useCallback(
throttle((point: Point2D, index: number) => {
console.log('handleReportNewPosition');
const offset = getContainerOffset(gravityRef);
if (!offset) return;

Expand All @@ -111,7 +109,6 @@ export const GravitySimulator: React.FC<GravitySimulatorProps> = ({
);

const handleDragEnd = () => {
console.log('handleDragEnd');
setTimeout(() => {
setIsDragging(false);
}, 0);
Expand All @@ -121,7 +118,6 @@ export const GravitySimulator: React.FC<GravitySimulatorProps> = ({

useEffect(() => {
const throttledUpdate = throttle((newPos: Point2D) => {
console.log('Moving mouse');
setThrottledPointerPos(newPos);
}, physicsConfig.DELTA_TIME * 1000);

Expand Down Expand Up @@ -221,8 +217,6 @@ export const GravitySimulator: React.FC<GravitySimulatorProps> = ({
);

const handleContainerClick = useCallback(() => {
console.log('handleContainerClick');
console.log(isDragging, isDraggingNewStar);
if (isDragging || isDraggingNewStar) return;

if (!isSimulationStarted) {
Expand Down Expand Up @@ -290,6 +284,11 @@ export const GravitySimulator: React.FC<GravitySimulatorProps> = ({
);

const handlePointDelete = useCallback((index: number) => {
console.log(
index,
gravityPoints,
gravityPoints.filter((_, i) => i !== index)
);
setGravityPoints((points) => points.filter((_, i) => i !== index));
}, []);

Expand Down
1 change: 1 addition & 0 deletions jest.config.js
Original file line number Diff line number Diff line change
Expand Up @@ -14,4 +14,5 @@ module.exports = {
testEnvironmentOptions: {
// Add custom JSDOM options if needed
},
fakeTimers: { enableGlobally: true },
};
25 changes: 19 additions & 6 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

4 changes: 3 additions & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@
"scripts": {
"start": "tsup --watch",
"build": "tsup",
"test": "jest",
"test": "jest --config jest.config.js",
"lint": "eslint \"src/**/*.{ts,tsx}\"",
"lint-fix": "eslint \"src/**/*.{ts,tsx}\" --fix",
"prepare": "tsup",
Expand Down Expand Up @@ -72,8 +72,10 @@
"@testing-library/jest-dom": "^6.6.3",
"@testing-library/react": "^14.2.1",
"@types/jest": "^29.5.14",
"@types/node": "^22.9.0",
"@types/react": "^18.3.12",
"@types/react-dom": "^18.3.1",
"@types/testing-library__jest-dom": "^5.14.9",
"@typescript-eslint/eslint-plugin": "^4.33.0",
"@typescript-eslint/parser": "^4.33.0",
"babel-loader": "^9.2.1",
Expand Down
4 changes: 2 additions & 2 deletions src/CustomCursor.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -92,7 +92,7 @@ export const CustomCursor: React.FC<CustomCursorProps> = React.memo(
}) => {
const { position, setPosition, targetPosition, isVisible } =
useMousePosition(containerRef, offsetX, offsetY);

console.log('>>>>>>>>>>>>isVisible', isVisible);
useSmoothAnimation(position, targetPosition, smoothFactor, setPosition);

const [portalContainer, setPortalContainer] =
Expand Down Expand Up @@ -176,7 +176,7 @@ export const CustomCursor: React.FC<CustomCursorProps> = React.memo(
// !portalContainer
// ),
// });

console.log('>>>>>>>>>>>>position', position);
if (
!isVisible ||
position.x === null ||
Expand Down
148 changes: 148 additions & 0 deletions test/CustomCursor.test.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,148 @@
import React from 'react';
import { render, fireEvent, act } from '@testing-library/react';
import { CustomCursor } from '../src';

describe('CustomCursor', () => {
// Helper to simulate mouse movement
const simulateMouseMove = (x: number, y: number) => {
fireEvent.mouseMove(document, {
clientX: x,
clientY: y,
});
};

beforeEach(() => {
// Reset any cursor containers from previous tests
const container = document.getElementById('cursor-container');
if (container) {
document.body.removeChild(container);
}
});

it('renders without crashing', () => {
render(<CustomCursor />);
expect(document.getElementById('cursor-container')).toBeInTheDocument();
});

it('creates and removes cursor container properly', () => {
const { unmount } = render(<CustomCursor />);
expect(document.getElementById('cursor-container')).toBeInTheDocument();

unmount();
expect(document.getElementById('cursor-container')).not.toBeInTheDocument();
});

it('follows mouse movement', () => {
render(<CustomCursor />);

act(() => {
simulateMouseMove(100, 100);
jest.advanceTimersByTime(100);
});

const cursor = document.querySelector('[id^="custom-cursor-"]');
expect(cursor).toHaveStyle({
transform: 'translate(100px, 100px)',
});
});

it('respects offset props', () => {
render(<CustomCursor offsetX={10} offsetY={20} />);

act(() => {
simulateMouseMove(100, 100);
jest.advanceTimersByTime(100);
});

const cursor = document.querySelector('[id^="custom-cursor-"]');
expect(cursor).toHaveStyle({
transform: 'translate(110px, 120px)',
});
});

it('calls onMove callback with cursor position', () => {
const onMove = jest.fn();
render(<CustomCursor onMove={onMove} />);

act(() => {
simulateMouseMove(100, 100);
jest.advanceTimersByTime(100);
});

expect(onMove).toHaveBeenCalledWith(100, 100);
});

it('applies custom styles', async () => {
const customStyle = { backgroundColor: 'red' };
render(<CustomCursor style={customStyle} />);

await act(async () => {
simulateMouseMove(100, 100);
jest.advanceTimersByTime(100);
});

// Look in the document body instead of the container
const cursor = document.querySelector('[id^="custom-cursor-"]');
expect(cursor).toHaveStyle({ backgroundColor: 'red' });
});

it('handles container-specific cursor behavior', async () => {
const containerRef = React.createRef<HTMLDivElement>();

render(
<>
<div
id="test-container"
ref={containerRef}
style={{
width: '200px',
height: '200px',
position: 'absolute',
top: 0,
left: 0,
}}
></div>
<CustomCursor containerRef={containerRef} />
</>
);
if (!containerRef.current) throw new Error('Container ref not found');
jest.spyOn(containerRef.current, 'getBoundingClientRect').mockReturnValue({
width: 200,
height: 200,
top: 0,
left: 0,
right: 200,
bottom: 200,
x: 0,
y: 0,
toJSON: () => {},
} as DOMRect);

await act(async () => {
if (!containerRef.current) throw new Error('Container ref not found');
console.log(containerRef.current);
// First trigger mouseEnter to set isVisible
fireEvent.mouseEnter(containerRef.current, {
clientX: 50,
clientY: 50,
bubbles: true,
cancelable: true,
});

// Then trigger mousemove ON THE CONTAINER to set position
fireEvent.mouseMove(containerRef.current, {
clientX: 50,
clientY: 50,
bubbles: true,
cancelable: true,
});

jest.runAllTimers();
});

const cursor = document.querySelector('[id^="custom-cursor-"]');
console.log('Found cursor:', !!cursor);

expect(cursor).toBeInTheDocument();
});
});
27 changes: 27 additions & 0 deletions test/hooks/useSmoothAnimation.test.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
import { renderHook } from '@testing-library/react';
import { useSmoothAnimation } from '../../src/hooks';

describe('useSmoothAnimation', () => {
beforeEach(() => {
jest.useFakeTimers();
});

afterEach(() => {
jest.useRealTimers();
});

it('smoothly animates position changes', () => {
const setPosition = jest.fn();
const position = { x: 0, y: 0 };
const targetPosition = { x: 100, y: 100 };

renderHook(() =>
useSmoothAnimation(position, targetPosition, 0.5, setPosition)
);

jest.advanceTimersByTime(16); // One frame
expect(setPosition).toHaveBeenCalled();
});

// Add more tests for the hook...
});
3 changes: 2 additions & 1 deletion tsconfig.json
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,8 @@
"noImplicitReturns": true,
"esModuleInterop": true,
"skipLibCheck": true,
"forceConsistentCasingInFileNames": true
"forceConsistentCasingInFileNames": true,
"types": ["jest", "@testing-library/jest-dom", "node"]
},
"include": ["src"],
"exclude": ["node_modules", "dist"]
Expand Down
9 changes: 9 additions & 0 deletions tsconfig.test.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
{
"extends": "./tsconfig.json",
"compilerOptions": {
"types": ["jest", "@testing-library/jest-dom"],
"isolatedModules": false,
"module": "commonjs"
},
"include": ["src", "test"]
}

0 comments on commit 107ebd5

Please sign in to comment.