Skip to content

Commit 1307d46

Browse files
committed
The one with mouse and touch events
1 parent b85e03e commit 1307d46

File tree

4 files changed

+75
-28
lines changed

4 files changed

+75
-28
lines changed

README.md

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,10 @@
1717
yarn add react-click-away-listener
1818
```
1919

20+
- It's quite small in size.
21+
- It's built with TypeScript.
22+
- It supports both Mouse and Touch Events.
23+
2024
## Usage
2125

2226
```jsx

__tests__/index.tsx

Lines changed: 52 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,9 @@ import ClickAwayListener from '../src';
55
describe('ClickAway Listener', () => {
66
it('should render properly', () => {
77
const { getByText } = render(
8-
<ClickAwayListener onClickAway={() => null}>Hello World</ClickAwayListener>
8+
<ClickAwayListener onClickAway={() => null}>
9+
Hello World
10+
</ClickAwayListener>
911
);
1012
expect(getByText(/Hello World/i)).toBeTruthy();
1113
});
@@ -22,48 +24,82 @@ describe('ClickAway Listener', () => {
2224
</React.Fragment>
2325
);
2426

27+
fireEvent.click(getByText(/A button/i));
28+
fireEvent.click(getByText(/A text element/i));
29+
fireEvent.click(getByText(/Hello World/i));
30+
expect(fakeHandleClick).toBeCalledTimes(2);
31+
});
32+
33+
it('works with different mouse events', () => {
34+
const fakeHandleClick = jest.fn();
35+
const { getByText } = render(
36+
<React.Fragment>
37+
<ClickAwayListener onClickAway={fakeHandleClick} mouseEvent="mousedown">
38+
Hello World
39+
</ClickAwayListener>
40+
<button>A button</button>
41+
<p>A text element</p>
42+
</React.Fragment>
43+
);
44+
2545
fireEvent.mouseDown(getByText(/A button/i));
2646
fireEvent.mouseDown(getByText(/A text element/i));
2747
fireEvent.mouseDown(getByText(/Hello World/i));
2848
expect(fakeHandleClick).toBeCalledTimes(2);
2949
});
3050

51+
it('works with different touch events', () => {
52+
const fakeHandleClick = jest.fn();
53+
const { getByText } = render(
54+
<React.Fragment>
55+
<ClickAwayListener onClickAway={fakeHandleClick} touchEvent="touchend">
56+
Hello World
57+
</ClickAwayListener>
58+
<button>A button</button>
59+
<p>A text element</p>
60+
</React.Fragment>
61+
);
62+
63+
fireEvent.touchEnd(getByText(/A button/i));
64+
fireEvent.touchEnd(getByText(/A text element/i));
65+
fireEvent.touchEnd(getByText(/Hello World/i));
66+
expect(fakeHandleClick).toBeCalledTimes(2);
67+
});
68+
3169
it('should handle multiple cases', () => {
3270
const fakeHandleClick = jest.fn();
3371
const fakeHandleClick2 = jest.fn();
3472
const { getByTestId } = render(
3573
<React.Fragment>
3674
<ClickAwayListener onClickAway={fakeHandleClick}>
37-
<div data-testid="hello-world">
38-
Hello World
39-
</div>
75+
<div data-testid="hello-world">Hello World</div>
4076
</ClickAwayListener>
4177
<button data-testid="button-one">A button</button>
4278
<button data-testid="some-other-button-one">Some other button</button>
4379
<p data-testid="text-one">A text element</p>
4480

4581
<ClickAwayListener onClickAway={fakeHandleClick2}>
46-
<div data-testid="foo-bar">
47-
Foo bar
48-
</div>
82+
<div data-testid="foo-bar">Foo bar</div>
4983
</ClickAwayListener>
5084
<button data-testid="button-two">Foo bar button</button>
51-
<button data-testid="some-other-button-two">Foo bar other button</button>
85+
<button data-testid="some-other-button-two">
86+
Foo bar other button
87+
</button>
5288
<p data-testid="text-two">Foo bar text element</p>
5389
</React.Fragment>
5490
);
5591

56-
fireEvent.mouseDown(getByTestId('button-one'));
57-
fireEvent.mouseDown(getByTestId('text-one'));
58-
fireEvent.mouseDown(getByTestId('hello-world'));
59-
fireEvent.mouseDown(getByTestId('some-other-button-one'));
92+
fireEvent.click(getByTestId('button-one'));
93+
fireEvent.click(getByTestId('text-one'));
94+
fireEvent.click(getByTestId('hello-world'));
95+
fireEvent.click(getByTestId('some-other-button-one'));
6096
expect(fakeHandleClick).toBeCalledTimes(3);
6197

6298
// 4 from the previous ones, and the 3 new ones
63-
fireEvent.mouseDown(getByTestId('button-two'));
64-
fireEvent.mouseDown(getByTestId('text-two'));
65-
fireEvent.mouseDown(getByTestId('foo-bar'));
66-
fireEvent.mouseDown(getByTestId('some-other-button-two'));
99+
fireEvent.click(getByTestId('button-two'));
100+
fireEvent.click(getByTestId('text-two'));
101+
fireEvent.click(getByTestId('foo-bar'));
102+
fireEvent.click(getByTestId('some-other-button-two'));
67103
expect(fakeHandleClick2).toBeCalledTimes(7);
68104
});
69105
});

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
{
22
"name": "react-click-away-listener",
3-
"version": "0.4.3",
3+
"version": "1.0.0",
44
"description": "A simple click away listener built with React Hooks",
55
"main": "dist/react-click-away-listener.js",
66
"module": "dist/react-click-away-listener.es.js",

src/index.tsx

Lines changed: 18 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1,34 +1,41 @@
11
import React, { useEffect, useRef, FunctionComponent } from 'react';
22

3+
type MouseEvents = 'click' | 'mousedown' | 'mouseup';
4+
type TouchEvents = 'touchstart' | 'touchend';
5+
36
interface Props {
47
onClickAway: Function;
8+
mouseEvent?: MouseEvents;
9+
touchEvent?: TouchEvents;
510
}
611

7-
const ClickAwayListener: FunctionComponent<Props> = ({ onClickAway, children }) => {
8-
12+
const ClickAwayListener: FunctionComponent<Props> = ({
13+
onClickAway,
14+
mouseEvent = 'click',
15+
touchEvent = 'touchend',
16+
children
17+
}) => {
918
let node = useRef<HTMLDivElement>(null);
1019

1120
useEffect(() => {
12-
const handleMouseDown = (event: MouseEvent): void => {
21+
const handleEvents = (event: MouseEvent | TouchEvent): void => {
1322
if (node.current && node.current.contains(event.target as Node)) {
1423
return;
1524
}
1625

1726
onClickAway();
18-
}
27+
};
1928

20-
document.addEventListener('mousedown', handleMouseDown);
29+
document.addEventListener(mouseEvent, handleEvents);
30+
document.addEventListener(touchEvent, handleEvents);
2131

2232
return () => {
23-
document.removeEventListener('mousedown', handleMouseDown);
33+
document.removeEventListener(mouseEvent, handleEvents);
34+
document.removeEventListener(touchEvent, handleEvents);
2435
};
2536
});
2637

27-
return (
28-
<div ref={node}>
29-
{children}
30-
</div>
31-
);
38+
return <div ref={node}>{children}</div>;
3239
};
3340

3441
export default ClickAwayListener;

0 commit comments

Comments
 (0)