@elah/editor 0.1.0 → 0.2.0
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 +127 -169
- package/dist/index.d.ts +1 -1
- package/dist/index.js +1 -1
- package/package.json +34 -5
package/README.md
CHANGED
|
@@ -1,169 +1,127 @@
|
|
|
1
|
-
# @elah/editor
|
|
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
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
```
|
|
129
|
-
|
|
130
|
-
Runs in a worker; reuses `resolveTimeline` + the renderer's placement math. See
|
|
131
|
-
[`src/core/export/README.md`](src/core/export/README.md).
|
|
132
|
-
|
|
133
|
-
## Package layout
|
|
134
|
-
|
|
135
|
-
```
|
|
136
|
-
src/
|
|
137
|
-
core/ types, engine, playback, resolver, stores, assets, media, export, debug, actions
|
|
138
|
-
timeline/ Timeline UI + hooks
|
|
139
|
-
editor/ EditorProvider, AssetPanel, Preview, useResolvedScene
|
|
140
|
-
```
|
|
141
|
-
|
|
142
|
-
## Keyboard shortcuts
|
|
143
|
-
|
|
144
|
-
The `<Timeline>` component registers these global keyboard shortcuts when focused:
|
|
145
|
-
|
|
146
|
-
| Key | Action |
|
|
147
|
-
|---|---|
|
|
148
|
-
| **Space** | Play / pause |
|
|
149
|
-
| **S** | Split selected clip at playhead |
|
|
150
|
-
| **Delete** / **Backspace** | Delete selected clip(s) |
|
|
151
|
-
| **Ctrl/Cmd + C** | Copy selected clip(s) to clipboard |
|
|
152
|
-
| **Ctrl/Cmd + V** | Paste copied clip(s) — placed at current playhead position, same track |
|
|
153
|
-
| **Ctrl/Cmd + Z** | Undo |
|
|
154
|
-
| **Ctrl/Cmd + Shift + Z** / **Ctrl/Cmd + Y** | Redo |
|
|
155
|
-
| **Ctrl/Cmd + scroll** | Zoom in / out |
|
|
156
|
-
| **← / →** | Step one frame back / forward |
|
|
157
|
-
|
|
158
|
-
**Right-click** any clip to open a context menu with a **Delete** option.
|
|
159
|
-
|
|
160
|
-
## Scripts
|
|
161
|
-
|
|
162
|
-
```bash
|
|
163
|
-
npm run typecheck # from packages/editor
|
|
164
|
-
npm run test
|
|
165
|
-
```
|
|
166
|
-
|
|
167
|
-
## License
|
|
168
|
-
|
|
169
|
-
To be decided — see root README.
|
|
1
|
+
# @elah/editor
|
|
2
|
+
|
|
3
|
+
The full Elah video editor SDK for React. Combines the core engine, timeline UI, WebGL2 renderer, media library, and export pipeline into a single package.
|
|
4
|
+
|
|
5
|
+
[](https://www.npmjs.com/package/@elah/editor)
|
|
6
|
+
[](https://github.com/elahlabs/elah/blob/main/LICENSE)
|
|
7
|
+
|
|
8
|
+
---
|
|
9
|
+
|
|
10
|
+
## Install
|
|
11
|
+
|
|
12
|
+
```bash
|
|
13
|
+
npm install @elah/editor
|
|
14
|
+
```
|
|
15
|
+
|
|
16
|
+
Peer dependencies: `react`, `react-dom` >= 18.
|
|
17
|
+
|
|
18
|
+
---
|
|
19
|
+
|
|
20
|
+
## Quick start
|
|
21
|
+
|
|
22
|
+
```tsx
|
|
23
|
+
import { EditorProvider, Timeline } from '@elah/editor'
|
|
24
|
+
|
|
25
|
+
function App() {
|
|
26
|
+
return (
|
|
27
|
+
<EditorProvider fps={30}>
|
|
28
|
+
<Timeline style={{ height: 300 }} />
|
|
29
|
+
</EditorProvider>
|
|
30
|
+
)
|
|
31
|
+
}
|
|
32
|
+
```
|
|
33
|
+
|
|
34
|
+
---
|
|
35
|
+
|
|
36
|
+
## With preview and asset panel
|
|
37
|
+
|
|
38
|
+
```tsx
|
|
39
|
+
import { EditorProvider, Timeline, Preview, AssetPanel, createMediabunnyBackend } from '@elah/editor'
|
|
40
|
+
import * as mediabunny from 'mediabunny'
|
|
41
|
+
|
|
42
|
+
const demuxerFactory = () =>
|
|
43
|
+
createMediabunnyBackend(mediabunny, {
|
|
44
|
+
blobResolver: (src) => fetch(src).then((r) => r.blob()),
|
|
45
|
+
})
|
|
46
|
+
|
|
47
|
+
function App() {
|
|
48
|
+
return (
|
|
49
|
+
<EditorProvider fps={30}>
|
|
50
|
+
<div style={{ display: 'flex', height: '100vh' }}>
|
|
51
|
+
<AssetPanel style={{ width: 220 }} />
|
|
52
|
+
<div style={{ flex: 1, display: 'flex', flexDirection: 'column' }}>
|
|
53
|
+
<Preview demuxerFactory={demuxerFactory} style={{ flex: 1 }} />
|
|
54
|
+
<Timeline style={{ height: 300 }} />
|
|
55
|
+
</div>
|
|
56
|
+
</div>
|
|
57
|
+
</EditorProvider>
|
|
58
|
+
)
|
|
59
|
+
}
|
|
60
|
+
```
|
|
61
|
+
|
|
62
|
+
---
|
|
63
|
+
|
|
64
|
+
## Import media
|
|
65
|
+
|
|
66
|
+
```ts
|
|
67
|
+
import { importFiles, useMediaLibrary } from '@elah/editor'
|
|
68
|
+
|
|
69
|
+
await importFiles(Array.from(fileList))
|
|
70
|
+
|
|
71
|
+
// Subscribe in React
|
|
72
|
+
const assets = useMediaLibrary(s => s.assets)
|
|
73
|
+
```
|
|
74
|
+
|
|
75
|
+
---
|
|
76
|
+
|
|
77
|
+
## Export to MP4
|
|
78
|
+
|
|
79
|
+
```ts
|
|
80
|
+
import { exportVideo } from '@elah/editor'
|
|
81
|
+
|
|
82
|
+
const blob = await exportVideo(engine.getProject(), {
|
|
83
|
+
videoBitrate: 8_000_000,
|
|
84
|
+
onProgress: ({ frame, totalFrames }) => {
|
|
85
|
+
console.log(`${Math.round((frame / totalFrames) * 100)}%`)
|
|
86
|
+
},
|
|
87
|
+
})
|
|
88
|
+
```
|
|
89
|
+
|
|
90
|
+
Runs in a web worker. Reuses `resolveTimeline` + the GPU renderer's placement math.
|
|
91
|
+
|
|
92
|
+
---
|
|
93
|
+
|
|
94
|
+
## Keyboard shortcuts
|
|
95
|
+
|
|
96
|
+
| Key | Action |
|
|
97
|
+
|---|---|
|
|
98
|
+
| `Space` | Play / pause |
|
|
99
|
+
| `S` | Split clip at playhead |
|
|
100
|
+
| `Delete` / `Backspace` | Delete selected clip(s) |
|
|
101
|
+
| `Ctrl/Cmd + C` | Copy |
|
|
102
|
+
| `Ctrl/Cmd + V` | Paste at playhead |
|
|
103
|
+
| `Ctrl/Cmd + Z` | Undo |
|
|
104
|
+
| `Ctrl/Cmd + Shift + Z` | Redo |
|
|
105
|
+
| `Ctrl/Cmd + scroll` | Zoom |
|
|
106
|
+
| `← / →` | Step one frame |
|
|
107
|
+
|
|
108
|
+
---
|
|
109
|
+
|
|
110
|
+
## Package layers
|
|
111
|
+
|
|
112
|
+
```
|
|
113
|
+
@elah/core — engine, playback, resolver, stores, media, export (framework-agnostic)
|
|
114
|
+
@elah/timeline — React timeline UI components and hooks
|
|
115
|
+
@elah/editor — EditorProvider, Preview, AssetPanel + re-exports everything above
|
|
116
|
+
```
|
|
117
|
+
|
|
118
|
+
Use `@elah/editor` for the full experience. Use `@elah/core` directly for headless or custom rendering pipelines.
|
|
119
|
+
|
|
120
|
+
---
|
|
121
|
+
|
|
122
|
+
## Links
|
|
123
|
+
|
|
124
|
+
- [Website](https://www.elah.dev)
|
|
125
|
+
- [GitHub](https://github.com/elahlabs/elah)
|
|
126
|
+
- [License](https://github.com/elahlabs/elah/blob/main/LICENSE)
|
|
127
|
+
- [Commercial licensing](mailto:contact@elah.dev)
|
package/dist/index.d.ts
CHANGED
|
@@ -9,7 +9,7 @@ export { GpuRenderer } from '@elah/core';
|
|
|
9
9
|
export type { RendererOptions } from '@elah/core';
|
|
10
10
|
export { GpuDebugCounters } from '@elah/core';
|
|
11
11
|
export type { CounterSnapshot } from '@elah/core';
|
|
12
|
-
export { createMediabunnyBackend, isMediabunnyCompatible } from '@elah/core';
|
|
12
|
+
export { createDefaultDemuxerFactory, createMediabunnyBackend, isMediabunnyCompatible } from '@elah/core';
|
|
13
13
|
export type { MediabunnyModule, CreateMediabunnyBackendOpts } from '@elah/core';
|
|
14
14
|
export type { DemuxerBackend, DemuxerFactory } from '@elah/core';
|
|
15
15
|
export type { VideoFrameProvider, VideoFrameProviderDeps } from '@elah/core';
|
package/dist/index.js
CHANGED
|
@@ -3,7 +3,7 @@ export { PlaybackEngine } from '@elah/core';
|
|
|
3
3
|
export { resolveTimeline } from '@elah/core';
|
|
4
4
|
export { GpuRenderer } from '@elah/core';
|
|
5
5
|
export { GpuDebugCounters } from '@elah/core';
|
|
6
|
-
export { createMediabunnyBackend, isMediabunnyCompatible } from '@elah/core';
|
|
6
|
+
export { createDefaultDemuxerFactory, createMediabunnyBackend, isMediabunnyCompatible } from '@elah/core';
|
|
7
7
|
export { createVideoFrameProvider, MockVideoFrameProvider, SyntheticVideoFrameProvider } from '@elah/core';
|
|
8
8
|
export { AudioPlaybackController } from '@elah/core';
|
|
9
9
|
export { useMediaLibrary, useMediaLibraryStore, MEDIA_DRAG_MIME, importFiles } from '@elah/core';
|
package/package.json
CHANGED
|
@@ -1,10 +1,11 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@elah/editor",
|
|
3
|
-
"version": "0.
|
|
4
|
-
"description": "
|
|
3
|
+
"version": "0.2.0",
|
|
4
|
+
"description": "Full React video editor SDK — timeline UI, WebGL2 preview, media library, drag and drop, and MP4 export",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "./dist/index.js",
|
|
7
7
|
"types": "./dist/index.d.ts",
|
|
8
|
+
"sideEffects": false,
|
|
8
9
|
"exports": {
|
|
9
10
|
".": {
|
|
10
11
|
"import": "./dist/index.js",
|
|
@@ -12,7 +13,9 @@
|
|
|
12
13
|
}
|
|
13
14
|
},
|
|
14
15
|
"files": [
|
|
15
|
-
"dist"
|
|
16
|
+
"dist",
|
|
17
|
+
"README.md",
|
|
18
|
+
"LICENSE"
|
|
16
19
|
],
|
|
17
20
|
"scripts": {
|
|
18
21
|
"typecheck": "tsc --noEmit",
|
|
@@ -20,13 +23,39 @@
|
|
|
20
23
|
"test:watch": "vitest",
|
|
21
24
|
"build": "tsc --noEmit && tsc -p tsconfig.build.json"
|
|
22
25
|
},
|
|
26
|
+
"keywords": [
|
|
27
|
+
"video-editor",
|
|
28
|
+
"react",
|
|
29
|
+
"sdk",
|
|
30
|
+
"timeline",
|
|
31
|
+
"webgl",
|
|
32
|
+
"webgl2",
|
|
33
|
+
"gpu",
|
|
34
|
+
"mp4",
|
|
35
|
+
"export",
|
|
36
|
+
"media-editor",
|
|
37
|
+
"browser-video-editor",
|
|
38
|
+
"video-sdk",
|
|
39
|
+
"asset-panel",
|
|
40
|
+
"preview",
|
|
41
|
+
"typescript"
|
|
42
|
+
],
|
|
43
|
+
"homepage": "https://www.elah.dev",
|
|
44
|
+
"repository": {
|
|
45
|
+
"type": "git",
|
|
46
|
+
"url": "https://github.com/elahlabs/elah.git"
|
|
47
|
+
},
|
|
48
|
+
"bugs": {
|
|
49
|
+
"url": "https://github.com/elahlabs/elah/issues"
|
|
50
|
+
},
|
|
51
|
+
"license": "SEE LICENSE IN LICENSE",
|
|
23
52
|
"peerDependencies": {
|
|
24
53
|
"react": ">=18.0.0",
|
|
25
54
|
"react-dom": ">=18.0.0"
|
|
26
55
|
},
|
|
27
56
|
"dependencies": {
|
|
28
|
-
"@elah/core": "
|
|
29
|
-
"@elah/timeline": "
|
|
57
|
+
"@elah/core": "^0.2.0",
|
|
58
|
+
"@elah/timeline": "^0.2.0",
|
|
30
59
|
"immer": "^10.1.1",
|
|
31
60
|
"zustand": "^5.0.3"
|
|
32
61
|
},
|