@sgrsoft/vpe-react-ui 0.2.12 → 0.2.14
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +259 -196
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -1,244 +1,307 @@
|
|
|
1
|
-
#
|
|
1
|
+
# vpe-react-ui
|
|
2
2
|
|
|
3
|
-
React
|
|
3
|
+
React 기반 비디오 플레이어 UI 컴포넌트 모음입니다. 스트리밍 엔진(HLS/DASH)은 외부에서 주입하고, UI는 이 패키지에서 제공합니다. 여러 플레이어를 동시에 렌더링할 수 있도록 스토어 스코프를 지원합니다.
|
|
4
|
+
|
|
5
|
+
## 주요 특징
|
|
6
|
+
|
|
7
|
+
- HLS/DASH/MP4/Native(HLS) 재생 UI 제공
|
|
8
|
+
- hls.js, dash.js는 선택적 주입(옵셔널 peer dependency)
|
|
9
|
+
- 자막 트랙(VTT) 지원 및 자막 선택/토글 UI 제공
|
|
10
|
+
- 품질 선택, 재생 속도, PiP, 전체화면, 음량, 공유 등 UI 컴포넌트 제공
|
|
11
|
+
- 모바일 더블탭 탐색 오버레이, 워터마크, 시작 시간 표시 등 부가 UI 제공
|
|
12
|
+
- `PlayerStoreProvider`로 플레이어별 상태 스코프 분리 가능
|
|
4
13
|
|
|
5
14
|
## 설치
|
|
15
|
+
|
|
6
16
|
```bash
|
|
7
17
|
pnpm add @sgrsoft/vpe-react-ui
|
|
8
|
-
# 선택: 스트리밍 라이브러리
|
|
9
|
-
pnpm add hls.js dashjs
|
|
10
18
|
```
|
|
11
|
-
- hls.js/dashjs는 선택적 peerDependency입니다. 브라우저/CDN 또는 `import Hls from "hls.js"`, `import dashjs from "dashjs"`로 주입하세요.
|
|
12
19
|
|
|
20
|
+
필수 peer dependency:
|
|
21
|
+
|
|
22
|
+
- `react`
|
|
23
|
+
- `react-dom`
|
|
24
|
+
|
|
25
|
+
선택적 주입:
|
|
26
|
+
|
|
27
|
+
- `hls.js`
|
|
28
|
+
- `dashjs`
|
|
29
|
+
|
|
30
|
+
## 기본 사용 예시
|
|
13
31
|
|
|
14
|
-
## 사용법
|
|
15
|
-
### React (ESM)
|
|
16
32
|
```tsx
|
|
33
|
+
import {
|
|
34
|
+
BaseStyle,
|
|
35
|
+
PlayerStoreProvider,
|
|
36
|
+
HlsVideo,
|
|
37
|
+
SeekBar,
|
|
38
|
+
PlayBtn,
|
|
39
|
+
CurrentTimeBtn,
|
|
40
|
+
DurationBtn,
|
|
41
|
+
VolumeBtn,
|
|
42
|
+
FullscreenBtn,
|
|
43
|
+
SettingBtn,
|
|
44
|
+
SettingModal,
|
|
45
|
+
} from "@sgrsoft/vpe-react-ui";
|
|
46
|
+
|
|
17
47
|
import Hls from "hls.js";
|
|
18
|
-
import dashjs from "dashjs";
|
|
19
|
-
import { VpePlayer } from "@sgrsoft/vpe-react-ui";
|
|
20
48
|
|
|
21
|
-
export function
|
|
49
|
+
export default function Player() {
|
|
50
|
+
const src = {
|
|
51
|
+
file: "https://example.com/stream.m3u8",
|
|
52
|
+
poster: "https://example.com/poster.jpg",
|
|
53
|
+
vtt: [
|
|
54
|
+
{ label: "KOR", id: "ko", default: true, src: "https://example.com/ko.vtt" },
|
|
55
|
+
],
|
|
56
|
+
};
|
|
57
|
+
|
|
58
|
+
const options = {
|
|
59
|
+
autostart: false,
|
|
60
|
+
autoPause: true,
|
|
61
|
+
objectFit: "contain",
|
|
62
|
+
playbackRate: 1,
|
|
63
|
+
lowLatencyMode: false,
|
|
64
|
+
};
|
|
65
|
+
|
|
22
66
|
return (
|
|
23
|
-
<
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
67
|
+
<PlayerStoreProvider>
|
|
68
|
+
<BaseStyle />
|
|
69
|
+
<div className="vpe-root-wrap">
|
|
70
|
+
<HlsVideo src={src} hlsLib={Hls} options={options} />
|
|
71
|
+
|
|
72
|
+
<div className="controls">
|
|
73
|
+
<SeekBar src={src} hlsLib={Hls} />
|
|
74
|
+
<PlayBtn />
|
|
75
|
+
<CurrentTimeBtn />
|
|
76
|
+
<DurationBtn />
|
|
77
|
+
<VolumeBtn />
|
|
78
|
+
<FullscreenBtn />
|
|
79
|
+
<SettingBtn />
|
|
80
|
+
</div>
|
|
81
|
+
|
|
82
|
+
<SettingModal
|
|
83
|
+
text={{
|
|
84
|
+
setting: "설정",
|
|
85
|
+
quality: "화질",
|
|
86
|
+
autoplay: "자동 재생",
|
|
87
|
+
playbackRate: "재생 속도",
|
|
88
|
+
captions: "자막",
|
|
89
|
+
auto: "자동",
|
|
90
|
+
notUse: "사용 안 함",
|
|
91
|
+
}}
|
|
92
|
+
src={src}
|
|
93
|
+
options={{ playRateSetting: [0.5, 1, 1.5, 2] }}
|
|
94
|
+
/>
|
|
95
|
+
</div>
|
|
96
|
+
</PlayerStoreProvider>
|
|
35
97
|
);
|
|
36
98
|
}
|
|
37
99
|
```
|
|
38
100
|
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
101
|
+
## 공통 레이아웃 규칙
|
|
102
|
+
|
|
103
|
+
- 루트 컨테이너에 `vpe-root-wrap` 클래스를 권장합니다.
|
|
104
|
+
- 전체화면 대상 엘리먼트를 지정하려면 `vpe-fullscreen-target` 클래스를 사용합니다.
|
|
105
|
+
- `BaseStyle` 컴포넌트는 필수는 아니지만 기본 스타일(폰트, 버튼, 모달, 오버레이 등)을 제공합니다.
|
|
106
|
+
|
|
107
|
+
## 비디오 컴포넌트
|
|
108
|
+
|
|
109
|
+
### `HlsVideo`
|
|
110
|
+
|
|
111
|
+
- hls.js가 주입되면 MSE 기반 HLS 재생을 사용합니다.
|
|
112
|
+
- hls.js 미지원 환경에서는 네이티브 HLS로 폴백합니다.
|
|
113
|
+
- `options.retry`로 재시도 횟수/간격을 설정할 수 있습니다.
|
|
114
|
+
- `options.lowLatencyMode` 사용 시 저지연 모드 설정을 시도합니다.
|
|
115
|
+
|
|
116
|
+
### `DashVideo`
|
|
117
|
+
|
|
118
|
+
- dash.js가 주입되면 DASH 재생을 사용합니다.
|
|
119
|
+
- dash.js 미주입 시 네이티브 재생으로 폴백합니다.
|
|
120
|
+
|
|
121
|
+
### `Mp4Video`
|
|
122
|
+
|
|
123
|
+
- 일반 MP4 재생용 컴포넌트입니다.
|
|
124
|
+
|
|
125
|
+
### `NativeVideo`
|
|
126
|
+
|
|
127
|
+
- 네이티브 HLS 재생 전용 컴포넌트입니다.
|
|
128
|
+
- FairPlay DRM 지원을 위한 `src.drm` 설정을 제공합니다.
|
|
129
|
+
|
|
130
|
+
#### 비디오 컴포넌트 공통 Props
|
|
131
|
+
|
|
132
|
+
```ts
|
|
133
|
+
src?: {
|
|
134
|
+
file?: string;
|
|
135
|
+
poster?: string;
|
|
136
|
+
vtt?: Array<{
|
|
137
|
+
label?: string;
|
|
138
|
+
id?: string;
|
|
139
|
+
default?: boolean;
|
|
140
|
+
src?: string;
|
|
141
|
+
}>;
|
|
142
|
+
drm?: Record<string, {
|
|
143
|
+
licenseUri?: string;
|
|
144
|
+
licenseRequestHeader?: Record<string, string | number>;
|
|
145
|
+
certificateUri?: string;
|
|
146
|
+
certificateRequestHeader?: Record<string, string | number>;
|
|
147
|
+
}>;
|
|
148
|
+
};
|
|
149
|
+
options?: {
|
|
150
|
+
autostart?: boolean;
|
|
151
|
+
autoPause?: boolean;
|
|
152
|
+
muted?: boolean;
|
|
153
|
+
objectFit?: string;
|
|
154
|
+
playbackRate?: number;
|
|
155
|
+
lowLatencyMode?: boolean;
|
|
156
|
+
retry?: { maxRetry?: number; interval?: number };
|
|
157
|
+
fairplayContentId?: string;
|
|
158
|
+
};
|
|
159
|
+
onError?: (err: unknown) => void;
|
|
160
|
+
emitEvent?: (type: string, data?: Record<string, unknown>) => void;
|
|
54
161
|
```
|
|
55
162
|
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
- `
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
```
|
|
81
|
-
- `.vpe-root-wrap`: 키보드/전체화면 처리에서 기준으로 사용하는 루트 클래스입니다. 플레이어 컨테이너에 적용을 권장합니다.
|
|
82
|
-
|
|
83
|
-
### 비디오 컴포넌트
|
|
84
|
-
모든 비디오 컴포넌트는 공통적으로 다음 props를 받습니다.
|
|
85
|
-
- `src`: `{ file, poster, vtt }` 형태의 소스. `vtt`는 자막 목록 배열입니다.
|
|
86
|
-
- `options`: 내부 동작 옵션. 공통적으로 `autoPause`, `playbackRate`를 지원합니다.
|
|
87
|
-
- `onError`: 에러 콜백.
|
|
88
|
-
- `emitEvent`: `useVideoStateEvents` 이벤트 훅(예: `"timeupdate"`, `"ended"` 등)을 외부로 전달합니다.
|
|
89
|
-
|
|
90
|
-
#### `HlsVideo`
|
|
91
|
-
- HLS(m3u8) 재생 컴포넌트입니다. `hlsLib`에 `hls.js` 인스턴스를 주입합니다.
|
|
92
|
-
- 추가 `options`: `lowLatencyMode`, `retry: { maxRetry, interval }`.
|
|
93
|
-
```tsx
|
|
94
|
-
import Hls from "hls.js";
|
|
95
|
-
import { HlsVideo } from "@sgrsoft/vpe-react-ui";
|
|
96
|
-
|
|
97
|
-
<HlsVideo
|
|
98
|
-
hlsLib={Hls}
|
|
99
|
-
src={{ file: "https://example.com/stream.m3u8", poster: "/poster.jpg" }}
|
|
100
|
-
options={{ lowLatencyMode: true, retry: { maxRetry: 3, interval: 3000 } }}
|
|
101
|
-
/>;
|
|
163
|
+
주의:
|
|
164
|
+
|
|
165
|
+
- `src.vtt`가 제공되면 해당 자막을 우선 사용합니다.
|
|
166
|
+
- `emitEvent`는 `timeupdate`, `ended`, `seeking`, `seeked`, `volumechange` 등 이벤트를 전달합니다.
|
|
167
|
+
- `NativeVideo`의 FairPlay DRM은 Safari 환경을 기준으로 구성되어 있습니다.
|
|
168
|
+
|
|
169
|
+
## UI 컨트롤 컴포넌트
|
|
170
|
+
|
|
171
|
+
### 공통 Props (`PlayBtnProps`)
|
|
172
|
+
|
|
173
|
+
```ts
|
|
174
|
+
size?: string;
|
|
175
|
+
weight?: "fill";
|
|
176
|
+
color?: string;
|
|
177
|
+
text?: any;
|
|
178
|
+
pos?: "left" | "right";
|
|
179
|
+
options?: any;
|
|
180
|
+
next?: () => void;
|
|
181
|
+
prev?: () => void;
|
|
182
|
+
pidx?: number;
|
|
183
|
+
playlistCnt?: number;
|
|
184
|
+
isMobile?: boolean;
|
|
185
|
+
isPortrait?: boolean;
|
|
186
|
+
isAnimationComplete?: boolean;
|
|
102
187
|
```
|
|
103
188
|
|
|
104
|
-
|
|
105
|
-
- MPEG-DASH(mpd) 재생 컴포넌트입니다. `dashLib`에 `dashjs` 인스턴스를 주입합니다.
|
|
106
|
-
- 추가 `options`: `autostart`, `retry: { maxRetry, interval }`.
|
|
107
|
-
```tsx
|
|
108
|
-
import dashjs from "dashjs";
|
|
109
|
-
import { DashVideo } from "@sgrsoft/vpe-react-ui";
|
|
110
|
-
|
|
111
|
-
<DashVideo
|
|
112
|
-
dashLib={dashjs}
|
|
113
|
-
src={{ file: "https://example.com/stream.mpd" }}
|
|
114
|
-
options={{ autostart: true }}
|
|
115
|
-
/>;
|
|
116
|
-
```
|
|
189
|
+
### 재생 관련
|
|
117
190
|
|
|
118
|
-
|
|
119
|
-
-
|
|
120
|
-
|
|
121
|
-
|
|
191
|
+
- `PlayBtn`: 재생/일시정지 토글 버튼
|
|
192
|
+
- `BigPlayBtn`: 중앙 대형 재생 버튼, 모바일에서 이전/다음과 함께 사용 가능
|
|
193
|
+
- `SkipBackBtn`: 기본 10초 뒤로, `options.skipSeconds`로 변경 가능
|
|
194
|
+
- `SkipForwardBtn`: 기본 10초 앞으로, `options.skipSeconds`로 변경 가능
|
|
122
195
|
|
|
123
|
-
|
|
124
|
-
```
|
|
196
|
+
### 시간 표시
|
|
125
197
|
|
|
126
|
-
|
|
127
|
-
-
|
|
128
|
-
-
|
|
129
|
-
```tsx
|
|
130
|
-
import { NativeVideo } from "@sgrsoft/vpe-react-ui";
|
|
198
|
+
- `TimeBtn`: 라이브 시 LIVE 버튼(라이브 엣지로 이동), VOD는 현재/전체 시간 표시
|
|
199
|
+
- `CurrentTimeBtn`: 현재 시간 표시
|
|
200
|
+
- `DurationBtn`: 전체 시간 표시
|
|
131
201
|
|
|
132
|
-
|
|
133
|
-
src={{
|
|
134
|
-
file: "https://example.com/stream.m3u8",
|
|
135
|
-
drm: {
|
|
136
|
-
"com.apple.fps": {
|
|
137
|
-
licenseUri: "https://license.example.com",
|
|
138
|
-
licenseRequestHeader: { Authorization: "Bearer token" },
|
|
139
|
-
certificateUri: "https://license.example.com/cert",
|
|
140
|
-
},
|
|
141
|
-
},
|
|
142
|
-
}}
|
|
143
|
-
/>;
|
|
144
|
-
```
|
|
202
|
+
### 음량/자막/화면
|
|
145
203
|
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
-
|
|
149
|
-
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
204
|
+
- `VolumeBtn`: 음소거 토글 + 볼륨 슬라이더
|
|
205
|
+
- `MuteBtn`: 음소거 토글 버튼만 제공
|
|
206
|
+
- `MuteIcon`: 음소거 상태 표시용 아이콘
|
|
207
|
+
- `SubtitleBtn`: 자막 토글
|
|
208
|
+
- `FullscreenBtn`: 전체화면 토글
|
|
209
|
+
- `PipBtn`: 브라우저 PiP 또는 `options.override.pip`로 커스텀 PiP
|
|
210
|
+
|
|
211
|
+
### 재생목록/네비게이션
|
|
212
|
+
|
|
213
|
+
- `PrevBtn`: 이전 콘텐츠로 이동
|
|
214
|
+
- `NextBtn`: 다음 콘텐츠로 이동
|
|
215
|
+
- `NextPrevBtn`: 이전/다음 버튼 묶음
|
|
158
216
|
|
|
159
|
-
|
|
217
|
+
### 부가 버튼
|
|
218
|
+
|
|
219
|
+
- `SettingBtn`: 설정 모달 열기
|
|
220
|
+
- `ShareBtn`: Web Share API 또는 클립보드 복사
|
|
221
|
+
|
|
222
|
+
## 설정 모달
|
|
223
|
+
|
|
224
|
+
### `SettingModal`
|
|
225
|
+
|
|
226
|
+
- 화질, 재생 속도, 자막 선택 UI 제공
|
|
227
|
+
- `usePlayerController`의 `selectQualityLevel`, `playBackRate`를 내부적으로 사용
|
|
228
|
+
|
|
229
|
+
```ts
|
|
230
|
+
text: {
|
|
231
|
+
setting: string;
|
|
232
|
+
quality: string;
|
|
233
|
+
autoplay: string;
|
|
234
|
+
playbackRate: string;
|
|
235
|
+
captions: string;
|
|
236
|
+
auto?: string;
|
|
237
|
+
notUse?: string;
|
|
238
|
+
};
|
|
239
|
+
vtt?: SubtitleTrack[];
|
|
240
|
+
src?: { vtt?: SubtitleTrack[] };
|
|
241
|
+
options?: { playRateSetting?: number[]; autostart?: boolean };
|
|
160
242
|
```
|
|
161
243
|
|
|
162
|
-
|
|
163
|
-
아래 버튼들은 공통적으로 `PlayBtnProps`를 사용합니다.
|
|
164
|
-
- 공통 props: `size`, `color`, `weight`, `pos`(팝오버 위치), `text`(라벨 문구), `options`.
|
|
244
|
+
## 오버레이/레이아웃 컴포넌트
|
|
165
245
|
|
|
166
|
-
|
|
167
|
-
-
|
|
246
|
+
- `InitPlayerUi`: 초기 플레이 버튼 오버레이
|
|
247
|
+
- `LoadingUi`: 로딩 스피너 오버레이
|
|
248
|
+
- `StartTimeUi`: 예약/시작 시간 카드 표시
|
|
249
|
+
- `WatermarkUi`: 워터마크 텍스트 표시(랜덤/고정 위치 지원)
|
|
250
|
+
- `DoubleTapSeekOverlay`: 모바일 더블탭 탐색 오버레이
|
|
251
|
+
- `MetaDesc`: 제목/프로필/작성시간 메타 정보 표시
|
|
252
|
+
- `Blank`: 레이아웃용 스페이서
|
|
253
|
+
- `Group`: 버튼 그룹 래퍼
|
|
168
254
|
|
|
169
|
-
|
|
170
|
-
- 중앙 재생 버튼입니다. 모바일/세로 화면에서만 클릭 동작을 수행합니다.
|
|
171
|
-
- 재생목록 컨트롤: `pidx`, `playlistCnt`, `next`, `prev`, `isMobile`, `isPortrait`.
|
|
255
|
+
### `DoubleTapSeekOverlay` Props
|
|
172
256
|
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
257
|
+
```ts
|
|
258
|
+
seekSeconds?: number;
|
|
259
|
+
doubleTapWindowMs?: number;
|
|
260
|
+
executeDelayMs?: number;
|
|
261
|
+
onSingleTap?: (side: "left" | "right") => void;
|
|
262
|
+
```
|
|
176
263
|
|
|
177
|
-
|
|
178
|
-
- 재생목록 이동 버튼입니다. `pidx`, `playlistCnt`, `prev`, `next` 필요.
|
|
264
|
+
## 훅/상태 관리
|
|
179
265
|
|
|
180
|
-
|
|
181
|
-
- 현재 시간/전체 길이를 표시합니다.
|
|
266
|
+
### `PlayerStoreProvider`
|
|
182
267
|
|
|
183
|
-
|
|
184
|
-
-
|
|
268
|
+
- 동일 페이지에서 여러 플레이어를 분리 관리하려면 반드시 사용합니다.
|
|
269
|
+
- `scopeId`를 직접 지정하거나 자동 생성합니다.
|
|
185
270
|
|
|
186
|
-
|
|
187
|
-
- 품질 레벨 선택 버튼입니다. `text.auto`로 Auto 라벨을 변경할 수 있습니다.
|
|
188
|
-
- `HlsVideo`/`DashVideo`가 로딩한 품질 목록(`playerState.levels`) 기반으로 동작합니다.
|
|
271
|
+
### `usePlayerState`
|
|
189
272
|
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
- 전체화면 토글 버튼입니다. `options.iosFullscreenNativeMode`로 iOS 대응을 제어합니다.
|
|
273
|
+
- 플레이어 상태를 읽고 패치합니다.
|
|
274
|
+
- 재생 상태, 로딩 상태, 자막/음량 상태, 화질 정보 등을 포함합니다.
|
|
193
275
|
|
|
194
|
-
|
|
195
|
-
- 자막 on/off 버튼입니다. `playerState.hasSubtitle`가 true일 때만 노출됩니다.
|
|
276
|
+
### `usePlayerController`
|
|
196
277
|
|
|
197
|
-
|
|
198
|
-
-
|
|
278
|
+
- 재생 제어 API를 제공합니다.
|
|
279
|
+
- 주요 메소드: `play`, `pause`, `togglePlay`, `seekTo`, `setVolume`, `toggleMute`, `toggleSubtitle`, `selectQualityLevel`, `togglePictureInPicture`, `toggleFullscreen`, `fullscreenOn`, `fullscreenOff` 등.
|
|
199
280
|
|
|
200
|
-
|
|
201
|
-
- 음소거 버튼 + 볼륨 슬라이더를 함께 제공합니다.
|
|
281
|
+
### `useDeviceState`
|
|
202
282
|
|
|
203
|
-
|
|
204
|
-
- 설정 모달 토글 버튼입니다. `playerState.isSettingModal`을 토글합니다.
|
|
283
|
+
- 미디어쿼리 기반으로 `isMobile`, `isPortrait` 상태를 제공합니다.
|
|
205
284
|
|
|
206
|
-
|
|
207
|
-
- Picture-in-Picture 토글 버튼입니다.
|
|
285
|
+
### `usePlayerKeyboardControls`
|
|
208
286
|
|
|
209
|
-
|
|
210
|
-
|
|
211
|
-
-
|
|
212
|
-
- props: `title`, `profileImage`, `profileName`, `createdAt`, `color`.
|
|
287
|
+
- 키보드 제어를 등록합니다.
|
|
288
|
+
- `options.keyboardShortcut`이 `true`일 때만 동작합니다.
|
|
289
|
+
- 단축키: Space(재생/일시정지), 좌/우(10초 이동), F(전체화면), M(음소거)
|
|
213
290
|
|
|
214
|
-
|
|
215
|
-
- 좌/우/중앙 정렬용 빈 공간 레이아웃 컴포넌트입니다.
|
|
216
|
-
- props: `align`(`left`/`right`/`center`), `style`, `children`.
|
|
291
|
+
## 유틸
|
|
217
292
|
|
|
218
|
-
|
|
219
|
-
- 버튼 그룹 래퍼입니다. 내부적으로 `BtnGroup`을 사용합니다.
|
|
220
|
-
- props: `noPadding`, `cap`(간격), `noBg`, `style`.
|
|
293
|
+
- `$util.formatTime(seconds)` 형태로 시간 문자열을 생성합니다.
|
|
221
294
|
|
|
222
|
-
|
|
223
|
-
#### `InitPlayerUi`
|
|
224
|
-
- 포스터 위에 초기 재생 버튼을 띄우는 오버레이입니다.
|
|
225
|
-
- props: `poster`, `options.objectFit`.
|
|
295
|
+
## 개발 명령
|
|
226
296
|
|
|
227
|
-
|
|
228
|
-
|
|
297
|
+
```bash
|
|
298
|
+
pnpm dev
|
|
299
|
+
pnpm build
|
|
300
|
+
pnpm preview
|
|
301
|
+
pnpm lint
|
|
302
|
+
```
|
|
229
303
|
|
|
230
|
-
|
|
231
|
-
- 모바일 더블탭 시킹 오버레이입니다.
|
|
232
|
-
- props:
|
|
233
|
-
- `seekSeconds`: 한번에 이동할 초(기본 10).
|
|
234
|
-
- `doubleTapWindowMs`: 더블탭 인식 시간(기본 300ms).
|
|
235
|
-
- `executeDelayMs`: 시킹 실행 지연(기본 300ms).
|
|
236
|
-
- `onSingleTap`: 단일 탭 콜백.
|
|
304
|
+
## 빌드 산출물
|
|
237
305
|
|
|
238
|
-
|
|
239
|
-
-
|
|
240
|
-
- props:
|
|
241
|
-
- `text`: `{ setting, quality, autoplay, playbackRate, captions, auto, notUse }` 라벨.
|
|
242
|
-
- `options.playRateSetting`: 재생 속도 선택 리스트(예: `[0.5, 1, 1.5, 2]`).
|
|
243
|
-
- `vtt` 또는 `src.vtt`: 자막 리스트.
|
|
244
|
-
- 표시 여부는 `usePlayerState`의 `isSettingModal` 상태로 제어하는 패턴을 권장합니다.
|
|
306
|
+
- ESM: `dist/vpe-react-ui.es.js`
|
|
307
|
+
- UMD: `dist/vpe-react-ui.umd.js`
|