Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions src/hooks/useLongPress/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
export { useLongPress } from './useLongPress.ts';
134 changes: 134 additions & 0 deletions src/hooks/useLongPress/ko/useLongPress.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,134 @@
# useLongPress

`useLongPress`는 요소가 지정된 시간 동안 눌리고 유지되는 것을 감지하는 리액트 훅이에요. 마우스와 터치 이벤트를 모두 처리하여 데스크톱과 모바일 기기에서 일관되게 작동해요.

## 인터페이스

```ts
function useLongPress<E extends HTMLElement>(
onLongPress: (event: React.MouseEvent<E> | React.TouchEvent<E>) => void,
options: UseOptionsObject
): Object;
```

### 파라미터

<Interface
required
name="onLongPress"
type="(event: React.MouseEvent<E> | React.TouchEvent<E>) => void"
description="길게 누르기가 감지될 때 실행되는 콜백 함수예요."
/>
<Interface
name="options"
type="Object"
description="길게 누르기 동작을 설정하는 옵션이에요."
:nested="[
{
name: 'options.delay',
type: 'number',
required: false,
defaultValue: '500',
description: '길게 누르기를 트리거하기 전 시간(밀리초)이에요. 기본값은 500ms예요.'
},
{
name: 'options.moveThreshold',
type: 'Object',
required: false,
description: '길게 누르기를 취소하기 전에 허용되는 최대 이동 거리예요.'
},
{
name: 'options.moveThreshold.x',
type: 'number',
required: false,
description: '최대 수평 이동 거리(픽셀)예요.'
},
{
name: 'options.moveThreshold.y',
type: 'number',
required: false,
description: '최대 수직 이동 거리(픽셀)예요.'
},
{
name: 'options.onClick',
type: '(event) => void',
required: false,
description: '일반 클릭(지연 시간 전에 누르고 떼기)에 실행되는 선택적 함수예요.'
},
{
name: 'options.onLongPressEnd',
type: '(event) => void',
required: false,
description: '길게 누르기가 끝날 때 실행되는 선택적 함수예요.'
}
]"
/>

### 반환 값

<Interface
name=""
type="Object"
description="JSX 요소에 전달할 이벤트 핸들러가 포함된 객체예요."
:nested="[
{
name: 'onMouseDown',
type: 'function',
description: '마우스 다운 이벤트 핸들러예요.'
},
{
name: 'onMouseUp',
type: 'function',
description: '마우스 업 이벤트 핸들러예요.'
},
{
name: 'onMouseLeave',
type: 'function',
description: '마우스 리브 이벤트 핸들러예요.'
},
{
name: 'onTouchStart',
type: 'function',
description: '터치 시작 이벤트 핸들러예요.'
},
{
name: 'onTouchEnd',
type: 'function',
description: '터치 종료 이벤트 핸들러예요.'
},
{
name: 'onTouchMove',
type: 'function',
description: '터치 이동 이벤트 핸들러예요 (moveThreshold가 지정된 경우에만 포함).'
},
{
name: 'onMouseMove',
type: 'function',
description: '마우스 이동 이벤트 핸들러예요 (moveThreshold가 지정된 경우에만 포함).'
}
]"
/>

## 예시

```tsx
import { useLongPress } from 'react-simplikit';
import { useState } from 'react';

function ContextMenu() {
const [menuVisible, setMenuVisible] = useState(false);

const longPressHandlers = useLongPress(() => setMenuVisible(true), {
delay: 400,
onClick: () => console.log('일반 클릭'),
onLongPressEnd: () => console.log('길게 누르기 완료'),
});

return (
<div>
<button {...longPressHandlers}>길게 누르세요</button>
{menuVisible && <div className="context-menu">컨텍스트 메뉴</div>}
</div>
);
}
```
134 changes: 134 additions & 0 deletions src/hooks/useLongPress/useLongPress.md
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@jiji-hoon96

Thank you for your hard work in writing the documentation. Just a quick tip — in react-simplikit, documentation is automatically generated from JSDoc using deployment action's generate-docs after merged! You might find the link below helpful:

Copy link
Copy Markdown
Contributor Author

@jiji-hoon96 jiji-hoon96 May 20, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for forwarding the documentation guide!

I didn't look closely enough at the contribution guide as I was working on it.
I spent more time writing the docs than I realized...🥲

Original file line number Diff line number Diff line change
@@ -0,0 +1,134 @@
# useLongPress

`useLongPress` is a React hook that detects when an element is pressed and held for a specified duration. It handles both mouse and touch events, making it work consistently across desktop and mobile devices.

## Interface

```ts
function useLongPress<E extends HTMLElement>(
onLongPress: (event: React.MouseEvent<E> | React.TouchEvent<E>) => void,
options: UseOptionsObject
): Object;
```

### Parameters

<Interface
required
name="onLongPress"
type="(event: React.MouseEvent<E> | React.TouchEvent<E>) => void"
description="The callback function to be executed when a long press is detected."
/>
<Interface
name="options"
type="Object"
description="Configuration options for the long press behavior."
:nested="[
{
name: 'options.delay',
type: 'number',
required: false,
defaultValue: '500',
description: 'The time in milliseconds before triggering the long press. Defaults to 500ms.'
},
{
name: 'options.moveThreshold',
type: 'Object',
required: false,
description: 'Maximum movement allowed before canceling a long press.'
},
{
name: 'options.moveThreshold.x',
type: 'number',
required: false,
description: 'Maximum horizontal movement in pixels.'
},
{
name: 'options.moveThreshold.y',
type: 'number',
required: false,
description: 'Maximum vertical movement in pixels.'
},
{
name: 'options.onClick',
type: '(event) => void',
required: false,
description: 'Optional function to execute on a normal click (press and release before delay).'
},
{
name: 'options.onLongPressEnd',
type: '(event) => void',
required: false,
description: 'Optional function to execute when a long press ends.'
}
]"
/>

### Return Value

<Interface
name=""
type="Object"
description="An object containing event handlers to spread onto a JSX element."
:nested="[
{
name: 'onMouseDown',
type: 'function',
description: 'Handler for mouse down events.'
},
{
name: 'onMouseUp',
type: 'function',
description: 'Handler for mouse up events.'
},
{
name: 'onMouseLeave',
type: 'function',
description: 'Handler for mouse leave events.'
},
{
name: 'onTouchStart',
type: 'function',
description: 'Handler for touch start events.'
},
{
name: 'onTouchEnd',
type: 'function',
description: 'Handler for touch end events.'
},
{
name: 'onTouchMove',
type: 'function',
description: 'Handler for touch move events (only included when moveThreshold is specified).'
},
{
name: 'onMouseMove',
type: 'function',
description: 'Handler for mouse move events (only included when moveThreshold is specified).'
}
]"
/>

## Example

```tsx
import { useLongPress } from 'react-simplikit';
import { useState } from 'react';

function ContextMenu() {
const [menuVisible, setMenuVisible] = useState(false);

const longPressHandlers = useLongPress(() => setMenuVisible(true), {
delay: 400,
onClick: () => console.log('Normal click'),
onLongPressEnd: () => console.log('Long press completed'),
});

return (
<div>
<button {...longPressHandlers}>Press and hold</button>
{menuVisible && <div className="context-menu">Context Menu</div>}
</div>
);
}
```
Loading
Loading