-
Notifications
You must be signed in to change notification settings - Fork 2
/
withIsPressed.tsx
65 lines (57 loc) · 2.1 KB
/
withIsPressed.tsx
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
/*---------------------------------------------------------------------------------------------
* Copyright (c) Bentley Systems, Incorporated. All rights reserved.
* See LICENSE.md in the project root for license terms and full copyright notice.
*--------------------------------------------------------------------------------------------*/
/** @packageDocumentation
* @module Common
*/
import * as React from "react";
/** Properties for [[withIsPressed]] React higher-order component
* @public
*/
export interface WithIsPressedProps {
/** initial value for pressed status */
isPressed?: boolean;
/** callback function for [isPressed] change */
onIsPressedChange?: (isPressed: boolean) => void;
}
/** withIsPressed is a React higher-order component that adds pointer and mouse events.
* @public
*/
export const withIsPressed = <ComponentProps extends {}>(
Component: React.ComponentType<ComponentProps>
) => {
return class WithIsPressed extends React.PureComponent<
ComponentProps & WithIsPressedProps
> {
public handleOnPointerDown = () => {
this.changeIsPressed(true);
};
public handleOnPointerUp = () => {
this.changeIsPressed(false);
};
public handleOnMouseLeave = () => {
this.changeIsPressed(false);
};
public changeIsPressed = (isPressed: boolean) => {
if (this.props.isPressed === isPressed) return;
this.props.onIsPressedChange && this.props.onIsPressedChange(isPressed);
};
public override render() {
const { isPressed, onIsPressedChange, ...props } = this.props; // todo: better solution to rest object of intersected type
return (
// eslint-disable-next-line jsx-a11y/no-static-element-interactions
<div
className="withispressed-wrapper"
onMouseDown={this.handleOnPointerDown}
onMouseUp={this.handleOnPointerUp}
onTouchStart={this.handleOnPointerDown}
onTouchEnd={this.handleOnPointerUp}
onMouseLeave={this.handleOnMouseLeave}
>
<Component {...(props as ComponentProps)} {...this.state} />
</div>
);
}
};
};