@next_term/react 0.1.0-next.7 → 0.1.0-next.9
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 +193 -0
- package/package.json +3 -3
package/README.md
ADDED
|
@@ -0,0 +1,193 @@
|
|
|
1
|
+
# @next_term/react
|
|
2
|
+
|
|
3
|
+
React components for the react-term terminal emulator.
|
|
4
|
+
|
|
5
|
+
## Install
|
|
6
|
+
|
|
7
|
+
```bash
|
|
8
|
+
npm install @next_term/react @next_term/core @next_term/web
|
|
9
|
+
```
|
|
10
|
+
|
|
11
|
+
## Basic Usage
|
|
12
|
+
|
|
13
|
+
```tsx
|
|
14
|
+
import { Terminal } from "@next_term/react";
|
|
15
|
+
import type { TerminalHandle } from "@next_term/react";
|
|
16
|
+
import { useEffect, useRef } from "react";
|
|
17
|
+
|
|
18
|
+
function App() {
|
|
19
|
+
const termRef = useRef<TerminalHandle>(null);
|
|
20
|
+
|
|
21
|
+
// Write PTY/WebSocket data to the terminal
|
|
22
|
+
useEffect(() => {
|
|
23
|
+
const ws = new WebSocket("ws://localhost:8080");
|
|
24
|
+
ws.binaryType = "arraybuffer";
|
|
25
|
+
ws.onmessage = (e) => termRef.current?.write(new Uint8Array(e.data));
|
|
26
|
+
return () => ws.close();
|
|
27
|
+
}, []);
|
|
28
|
+
|
|
29
|
+
return (
|
|
30
|
+
<Terminal
|
|
31
|
+
ref={termRef}
|
|
32
|
+
autoFit
|
|
33
|
+
fontSize={14}
|
|
34
|
+
fontFamily="monospace"
|
|
35
|
+
onData={(data) => {
|
|
36
|
+
// User typed something — send to your backend
|
|
37
|
+
ws.send(data);
|
|
38
|
+
}}
|
|
39
|
+
onResize={({ cols, rows }) => {
|
|
40
|
+
// Terminal was resized — notify PTY
|
|
41
|
+
ws.send(`\x1b[8;${rows};${cols}t`);
|
|
42
|
+
}}
|
|
43
|
+
/>
|
|
44
|
+
);
|
|
45
|
+
}
|
|
46
|
+
```
|
|
47
|
+
|
|
48
|
+
## Multi-Pane Layout
|
|
49
|
+
|
|
50
|
+
`<TerminalPane>` manages multiple terminals in a split layout with a single shared WebGL context (avoids Chrome's 16-context limit).
|
|
51
|
+
|
|
52
|
+
```tsx
|
|
53
|
+
import { TerminalPane } from "@next_term/react";
|
|
54
|
+
import type { TerminalPaneHandle, PaneLayout } from "@next_term/react";
|
|
55
|
+
|
|
56
|
+
const layout: PaneLayout = {
|
|
57
|
+
type: "horizontal",
|
|
58
|
+
children: [
|
|
59
|
+
{ type: "single", id: "editor" },
|
|
60
|
+
{
|
|
61
|
+
type: "vertical",
|
|
62
|
+
children: [
|
|
63
|
+
{ type: "single", id: "terminal" },
|
|
64
|
+
{ type: "single", id: "logs" },
|
|
65
|
+
],
|
|
66
|
+
sizes: [0.6, 0.4],
|
|
67
|
+
},
|
|
68
|
+
],
|
|
69
|
+
sizes: [0.5, 0.5],
|
|
70
|
+
};
|
|
71
|
+
|
|
72
|
+
function IDE() {
|
|
73
|
+
const paneRef = useRef<TerminalPaneHandle>(null);
|
|
74
|
+
|
|
75
|
+
return (
|
|
76
|
+
<TerminalPane
|
|
77
|
+
ref={paneRef}
|
|
78
|
+
layout={layout}
|
|
79
|
+
fontSize={13}
|
|
80
|
+
fontFamily="monospace"
|
|
81
|
+
onData={(paneId, data) => {
|
|
82
|
+
connections.get(paneId)?.send(data);
|
|
83
|
+
}}
|
|
84
|
+
style={{ width: "100%", height: "100vh" }}
|
|
85
|
+
/>
|
|
86
|
+
);
|
|
87
|
+
}
|
|
88
|
+
|
|
89
|
+
// Write to a specific pane
|
|
90
|
+
paneRef.current?.getTerminal("logs")?.write("Build complete.\r\n");
|
|
91
|
+
```
|
|
92
|
+
|
|
93
|
+
## Props
|
|
94
|
+
|
|
95
|
+
### `<Terminal>`
|
|
96
|
+
|
|
97
|
+
| Prop | Type | Default | Description |
|
|
98
|
+
|------|------|---------|-------------|
|
|
99
|
+
| `cols` | `number` | `80` | Initial column count |
|
|
100
|
+
| `rows` | `number` | `24` | Initial row count |
|
|
101
|
+
| `fontSize` | `number` | `16` | Font size in pixels |
|
|
102
|
+
| `fontFamily` | `string` | `"'Courier New', monospace"` | CSS font-family |
|
|
103
|
+
| `fontWeight` | `number` | `400` | Normal text weight |
|
|
104
|
+
| `fontWeightBold` | `number` | `700` | Bold text weight |
|
|
105
|
+
| `theme` | `Partial<Theme>` | Dark theme | Terminal colors |
|
|
106
|
+
| `scrollback` | `number` | `1000` | Scrollback buffer lines |
|
|
107
|
+
| `autoFit` | `boolean` | `false` | Auto-resize to container |
|
|
108
|
+
| `renderer` | `"auto" \| "webgl" \| "canvas2d"` | `"auto"` | Rendering backend |
|
|
109
|
+
| `renderMode` | `"auto" \| "offscreen" \| "main"` | `"auto"` | Where rendering runs |
|
|
110
|
+
| `useWorker` | `boolean` | auto | VT parser in Web Worker |
|
|
111
|
+
| `sharedContext` | `SharedWebGLContext` | -- | Shared WebGL context for multi-pane |
|
|
112
|
+
| `paneId` | `string` | -- | Pane ID (required with sharedContext) |
|
|
113
|
+
| `onData` | `(data: Uint8Array) => void` | -- | User input callback |
|
|
114
|
+
| `onResize` | `(size) => void` | -- | Resize callback |
|
|
115
|
+
| `onTitleChange` | `(title: string) => void` | -- | OSC title change |
|
|
116
|
+
| `className` | `string` | -- | CSS class on container |
|
|
117
|
+
| `style` | `React.CSSProperties` | -- | Inline styles on container |
|
|
118
|
+
|
|
119
|
+
### `<TerminalPane>`
|
|
120
|
+
|
|
121
|
+
| Prop | Type | Description |
|
|
122
|
+
|------|------|-------------|
|
|
123
|
+
| `layout` | `PaneLayout` | Split layout tree |
|
|
124
|
+
| `onData` | `(paneId, data) => void` | Input from any pane |
|
|
125
|
+
| `fontSize` | `number` | Shared font size |
|
|
126
|
+
| `fontFamily` | `string` | Shared font family |
|
|
127
|
+
| `fontWeight` | `number` | Shared normal text weight |
|
|
128
|
+
| `fontWeightBold` | `number` | Shared bold text weight |
|
|
129
|
+
| `theme` | `Partial<Theme>` | Shared theme |
|
|
130
|
+
| `className` | `string` | CSS class on root container |
|
|
131
|
+
| `style` | `React.CSSProperties` | Inline styles on root container |
|
|
132
|
+
|
|
133
|
+
### `TerminalPaneHandle`
|
|
134
|
+
|
|
135
|
+
```ts
|
|
136
|
+
interface TerminalPaneHandle {
|
|
137
|
+
getTerminal(paneId: string): TerminalHandle | null;
|
|
138
|
+
getPaneIds(): string[];
|
|
139
|
+
}
|
|
140
|
+
```
|
|
141
|
+
|
|
142
|
+
### `TerminalHandle`
|
|
143
|
+
|
|
144
|
+
```ts
|
|
145
|
+
interface TerminalHandle {
|
|
146
|
+
write(data: string | Uint8Array): void;
|
|
147
|
+
resize(cols: number, rows: number): void;
|
|
148
|
+
focus(): void;
|
|
149
|
+
blur(): void;
|
|
150
|
+
fit(): void;
|
|
151
|
+
}
|
|
152
|
+
```
|
|
153
|
+
|
|
154
|
+
## Best Practices
|
|
155
|
+
|
|
156
|
+
### Font Configuration
|
|
157
|
+
|
|
158
|
+
Use generic families or system-installed fonts. Web fonts loaded via `@font-face` are loaded automatically via the CSS Font Loading API, but may cause a brief flash of fallback text (FOUT) on first render:
|
|
159
|
+
|
|
160
|
+
```tsx
|
|
161
|
+
// Good: generic family, always available
|
|
162
|
+
<Terminal fontFamily="monospace" />
|
|
163
|
+
|
|
164
|
+
// Good: system font with generic fallback
|
|
165
|
+
<Terminal fontFamily="'Menlo', 'Consolas', monospace" />
|
|
166
|
+
|
|
167
|
+
// Works: web font — loaded async, brief FOUT on first render
|
|
168
|
+
<Terminal fontFamily="'Fira Code', monospace" />
|
|
169
|
+
```
|
|
170
|
+
|
|
171
|
+
### COOP/COEP Headers for Worker Support
|
|
172
|
+
|
|
173
|
+
SharedArrayBuffer (required for Web Worker parsing) needs cross-origin isolation. Without these headers, the terminal falls back to main-thread parsing automatically:
|
|
174
|
+
|
|
175
|
+
```
|
|
176
|
+
Cross-Origin-Opener-Policy: same-origin
|
|
177
|
+
Cross-Origin-Embedder-Policy: require-corp
|
|
178
|
+
```
|
|
179
|
+
|
|
180
|
+
### Theme
|
|
181
|
+
|
|
182
|
+
```tsx
|
|
183
|
+
import { DEFAULT_THEME } from "@next_term/core";
|
|
184
|
+
|
|
185
|
+
// Override specific colors
|
|
186
|
+
<Terminal theme={{ background: "#1a1b26", foreground: "#c0caf5" }} />
|
|
187
|
+
```
|
|
188
|
+
|
|
189
|
+
All CSS color formats are supported: `#rgb`, `#rrggbb`, `rgb()`, `hsl()`, `oklch()`, named colors.
|
|
190
|
+
|
|
191
|
+
## License
|
|
192
|
+
|
|
193
|
+
MIT
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@next_term/react",
|
|
3
|
-
"version": "0.1.0-next.
|
|
3
|
+
"version": "0.1.0-next.9",
|
|
4
4
|
"license": "MIT",
|
|
5
5
|
"repository": {
|
|
6
6
|
"type": "git",
|
|
@@ -28,8 +28,8 @@
|
|
|
28
28
|
"react-dom": "^18.0.0 || ^19.0.0"
|
|
29
29
|
},
|
|
30
30
|
"dependencies": {
|
|
31
|
-
"@next_term/
|
|
32
|
-
"@next_term/
|
|
31
|
+
"@next_term/web": "0.1.0-next.9",
|
|
32
|
+
"@next_term/core": "0.0.1-next.9"
|
|
33
33
|
},
|
|
34
34
|
"devDependencies": {
|
|
35
35
|
"typescript": "^5.5.0",
|