node-mac-recorder 2.1.1 → 2.1.2
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 +79 -17
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
# node-mac-recorder
|
|
2
2
|
|
|
3
|
-
A powerful native macOS screen recording Node.js package with advanced window selection, multi-display support, and granular audio controls. Built with AVFoundation for optimal performance.
|
|
3
|
+
A powerful native macOS screen recording Node.js package with advanced window selection, multi-display support, and granular audio controls. Built with AVFoundation and ScreenCaptureKit for optimal performance.
|
|
4
4
|
|
|
5
5
|
## Features
|
|
6
6
|
|
|
@@ -12,6 +12,7 @@ A powerful native macOS screen recording Node.js package with advanced window se
|
|
|
12
12
|
- 🖱️ **Multi-Display Support** - Automatic display detection and selection
|
|
13
13
|
- 🎨 **Cursor Control** - Toggle cursor visibility in recordings
|
|
14
14
|
- 🖱️ **Cursor Tracking** - Track mouse position, cursor types, and click events
|
|
15
|
+
- 🚫 **Exclude Apps/Windows (macOS 15+)** - Use ScreenCaptureKit to exclude specific apps (bundle id/PID) and windows
|
|
15
16
|
|
|
16
17
|
🎵 **Granular Audio Controls**
|
|
17
18
|
|
|
@@ -49,6 +50,11 @@ npm install node-mac-recorder
|
|
|
49
50
|
- **Screen Recording Permission** (automatically requested)
|
|
50
51
|
- **CPU Architecture**: Intel (x64) and Apple Silicon (ARM64) supported
|
|
51
52
|
|
|
53
|
+
ScreenCaptureKit path and exclusion support:
|
|
54
|
+
|
|
55
|
+
- Requires macOS 15.0+ for on-disk recording via `SCRecordingOutput`
|
|
56
|
+
- On older systems (<=14), the library falls back to AVFoundation automatically (exclusions not available)
|
|
57
|
+
|
|
52
58
|
### Build Requirements
|
|
53
59
|
|
|
54
60
|
```bash
|
|
@@ -110,9 +116,22 @@ await recorder.startRecording("./recording.mov", {
|
|
|
110
116
|
quality: "high", // 'low', 'medium', 'high'
|
|
111
117
|
frameRate: 30, // FPS (15, 30, 60)
|
|
112
118
|
captureCursor: false, // Show cursor (default: false)
|
|
119
|
+
|
|
120
|
+
// ScreenCaptureKit (macOS 15+) - optional, backward compatible
|
|
121
|
+
useScreenCaptureKit: false, // If true and available, prefers ScreenCaptureKit
|
|
122
|
+
excludedAppBundleIds: ["com.apple.Safari"], // Exclude by bundle id
|
|
123
|
+
excludedPIDs: [process.pid], // Exclude by PID
|
|
124
|
+
excludedWindowIds: [12345, 67890], // Exclude specific window IDs
|
|
125
|
+
// When running under Electron, autoExcludeSelf defaults to true
|
|
126
|
+
autoExcludeSelf: true,
|
|
113
127
|
});
|
|
114
128
|
```
|
|
115
129
|
|
|
130
|
+
Notes
|
|
131
|
+
|
|
132
|
+
- If any of `excludedAppBundleIds`, `excludedPIDs`, `excludedWindowIds` are provided, the library automatically switches to ScreenCaptureKit on supported macOS versions.
|
|
133
|
+
- When running inside Electron, the current app PID is excluded by default (`autoExcludeSelf: true`).
|
|
134
|
+
|
|
116
135
|
#### `stopRecording()`
|
|
117
136
|
|
|
118
137
|
Stops the current recording.
|
|
@@ -305,6 +324,29 @@ await new Promise((resolve) => setTimeout(resolve, 10000)); // 10 seconds
|
|
|
305
324
|
await recorder.stopRecording();
|
|
306
325
|
```
|
|
307
326
|
|
|
327
|
+
### Exclude Electron app and other windows (ScreenCaptureKit)
|
|
328
|
+
|
|
329
|
+
```javascript
|
|
330
|
+
const recorder = new MacRecorder();
|
|
331
|
+
|
|
332
|
+
// By default, when running inside Electron, your app is auto-excluded.
|
|
333
|
+
// You can also exclude other apps/windows explicitly:
|
|
334
|
+
await recorder.startRecording("./excluded.mov", {
|
|
335
|
+
captureCursor: true,
|
|
336
|
+
// Prefer SC explicitly (optional — auto-enabled when exclusions are set)
|
|
337
|
+
useScreenCaptureKit: true,
|
|
338
|
+
excludedAppBundleIds: ["com.apple.Safari"],
|
|
339
|
+
excludedWindowIds: [
|
|
340
|
+
/* CGWindowID list */
|
|
341
|
+
],
|
|
342
|
+
// autoExcludeSelf is true by default on Electron; set false to include your app
|
|
343
|
+
// autoExcludeSelf: false,
|
|
344
|
+
});
|
|
345
|
+
|
|
346
|
+
// ... later
|
|
347
|
+
await recorder.stopRecording();
|
|
348
|
+
```
|
|
349
|
+
|
|
308
350
|
### Multi-Display Recording
|
|
309
351
|
|
|
310
352
|
```javascript
|
|
@@ -362,16 +404,17 @@ audioDevices.forEach((device, i) => {
|
|
|
362
404
|
});
|
|
363
405
|
|
|
364
406
|
// Find system audio device (like BlackHole, Soundflower, etc.)
|
|
365
|
-
const systemAudioDevice = audioDevices.find(
|
|
366
|
-
device
|
|
367
|
-
|
|
368
|
-
|
|
369
|
-
|
|
407
|
+
const systemAudioDevice = audioDevices.find(
|
|
408
|
+
(device) =>
|
|
409
|
+
device.name.toLowerCase().includes("blackhole") ||
|
|
410
|
+
device.name.toLowerCase().includes("soundflower") ||
|
|
411
|
+
device.name.toLowerCase().includes("loopback") ||
|
|
412
|
+
device.name.toLowerCase().includes("aggregate")
|
|
370
413
|
);
|
|
371
414
|
|
|
372
415
|
if (systemAudioDevice) {
|
|
373
416
|
console.log(`Using system audio device: ${systemAudioDevice.name}`);
|
|
374
|
-
|
|
417
|
+
|
|
375
418
|
// Record with specific system audio device
|
|
376
419
|
await recorder.startRecording("./system-audio-specific.mov", {
|
|
377
420
|
includeMicrophone: false,
|
|
@@ -380,8 +423,10 @@ if (systemAudioDevice) {
|
|
|
380
423
|
captureArea: { x: 0, y: 0, width: 1, height: 1 }, // Minimal video
|
|
381
424
|
});
|
|
382
425
|
} else {
|
|
383
|
-
console.log(
|
|
384
|
-
|
|
426
|
+
console.log(
|
|
427
|
+
"No system audio device found. Installing BlackHole or Soundflower recommended."
|
|
428
|
+
);
|
|
429
|
+
|
|
385
430
|
// Record with default system audio capture (may not work without virtual audio device)
|
|
386
431
|
await recorder.startRecording("./system-audio-default.mov", {
|
|
387
432
|
includeMicrophone: false,
|
|
@@ -391,7 +436,7 @@ if (systemAudioDevice) {
|
|
|
391
436
|
}
|
|
392
437
|
|
|
393
438
|
// Record for 10 seconds
|
|
394
|
-
await new Promise(resolve => setTimeout(resolve, 10000));
|
|
439
|
+
await new Promise((resolve) => setTimeout(resolve, 10000));
|
|
395
440
|
await recorder.stopRecording();
|
|
396
441
|
```
|
|
397
442
|
|
|
@@ -400,7 +445,7 @@ await recorder.stopRecording();
|
|
|
400
445
|
For reliable system audio capture, install a virtual audio device:
|
|
401
446
|
|
|
402
447
|
1. **BlackHole** (Free): https://github.com/ExistentialAudio/BlackHole
|
|
403
|
-
2. **Soundflower** (Free): https://github.com/mattingalls/Soundflower
|
|
448
|
+
2. **Soundflower** (Free): https://github.com/mattingalls/Soundflower
|
|
404
449
|
3. **Loopback** (Paid): https://rogueamoeba.com/loopback/
|
|
405
450
|
|
|
406
451
|
These create aggregate audio devices that the package can detect and use for system audio capture.
|
|
@@ -720,6 +765,11 @@ npm cache clean --force
|
|
|
720
765
|
xcode-select --install
|
|
721
766
|
```
|
|
722
767
|
|
|
768
|
+
### ScreenCaptureKit availability
|
|
769
|
+
|
|
770
|
+
- Exclusions require macOS 15+ (uses `SCRecordingOutput`).
|
|
771
|
+
- On macOS 12.3–14, the module will fall back to AVFoundation (no exclusions). This is automatic and backward-compatible.
|
|
772
|
+
|
|
723
773
|
### Recording Issues
|
|
724
774
|
|
|
725
775
|
1. **Empty/Black Video**: Check screen recording permissions
|
|
@@ -774,12 +824,24 @@ MIT License - see [LICENSE](LICENSE) file for details.
|
|
|
774
824
|
|
|
775
825
|
### Latest Updates
|
|
776
826
|
|
|
777
|
-
- ✅
|
|
778
|
-
- ✅
|
|
779
|
-
- ✅
|
|
780
|
-
- ✅
|
|
781
|
-
- ✅
|
|
782
|
-
- ✅
|
|
827
|
+
- ✅ ScreenCaptureKit path with exclusions (apps by bundle id/PID and window IDs) on macOS 15+
|
|
828
|
+
- ✅ Electron apps auto-excluded by default (can be disabled with `autoExcludeSelf: false`)
|
|
829
|
+
- ✅ Prebuilt binaries for darwin-arm64 and darwin-x64; automatic loading via `node-gyp-build`
|
|
830
|
+
- ✅ Cursor Tracking: Track mouse position, cursor types, and click events with JSON export
|
|
831
|
+
- ✅ Window Recording: Automatic coordinate conversion for multi-display setups
|
|
832
|
+
- ✅ Audio Controls: Separate microphone and system audio controls
|
|
833
|
+
- ✅ Display Selection: Multi-monitor support with automatic detection
|
|
834
|
+
- ✅ Smart Filtering: Improved window detection and filtering
|
|
835
|
+
- ✅ Performance: Optimized native implementation
|
|
836
|
+
|
|
837
|
+
## Prebuilt binaries
|
|
838
|
+
|
|
839
|
+
This package ships prebuilt native binaries for macOS:
|
|
840
|
+
|
|
841
|
+
- darwin-arm64 (Apple Silicon)
|
|
842
|
+
- darwin-x64 (Intel)
|
|
843
|
+
|
|
844
|
+
At runtime, the correct binary is loaded automatically via `node-gyp-build`. If a prebuilt is not available for your environment, the module falls back to a local build.
|
|
783
845
|
|
|
784
846
|
---
|
|
785
847
|
|