CoPilot Github: Stream fex 3
This commit is contained in:
@@ -232,13 +232,15 @@ class CameraSwitch extends EventEmitter {
|
||||
// 1. Live-FFmpeg beenden, auf Prozess-Ende warten (= Device-FD frei)
|
||||
await this._killCurrentAndWait();
|
||||
|
||||
// 2. Kamera resetten: kurz warten, dann zwischenformat öffnen, wieder warten.
|
||||
// 2. Kamera resetten: kurz warten, dann Zwischenformat öffnen, wieder warten.
|
||||
await sleep(800);
|
||||
const warmupSize = this._chooseWarmupSize();
|
||||
if (warmupSize) {
|
||||
console.log(`[cam ${this.id}] HD: Zwischenformat ${warmupSize} zum Kamera-Reset`);
|
||||
await this._warmupFormat(warmupSize);
|
||||
await sleep(500);
|
||||
} else {
|
||||
console.log(`[cam ${this.id}] HD: Kein Zwischenformat nötig (live ${this.liveSize} → hires ${this.hiresSize})`);
|
||||
}
|
||||
|
||||
this.state = 'grabbing';
|
||||
@@ -283,6 +285,7 @@ class CameraSwitch extends EventEmitter {
|
||||
|
||||
_warmupFormat(size) {
|
||||
return new Promise((resolve) => {
|
||||
console.log(`[cam ${this.id}] HD: Warmup-Format ${size} starten`);
|
||||
const args = [
|
||||
'-hide_banner', '-loglevel', 'warning',
|
||||
'-fflags', 'nobuffer',
|
||||
@@ -295,6 +298,7 @@ class CameraSwitch extends EventEmitter {
|
||||
try {
|
||||
p = spawn('ffmpeg', args, { stdio: ['ignore', 'pipe', 'ignore'] });
|
||||
} catch (_e) {
|
||||
console.warn(`[cam ${this.id}] warmup ffmpeg start fehlgeschlagen: ${_e.message}`);
|
||||
return resolve();
|
||||
}
|
||||
this.proc = p;
|
||||
@@ -307,12 +311,18 @@ class CameraSwitch extends EventEmitter {
|
||||
if (p) {
|
||||
try { p.kill('SIGTERM'); } catch (_e) {}
|
||||
}
|
||||
console.log(`[cam ${this.id}] HD: Warmup-Format ${size} beendet`);
|
||||
resolve();
|
||||
};
|
||||
|
||||
p.stderr.on('data', (c) => {
|
||||
const s = c.toString();
|
||||
if (/error|busy|invalid|no such|cannot|denied/i.test(s)) console.error(`[cam ${this.id}] warmup ffmpeg: ${s.trim()}`);
|
||||
const s = c.toString().trim();
|
||||
if (!s) return;
|
||||
if (/error|busy|invalid|no such|cannot|denied/i.test(s)) {
|
||||
console.warn(`[cam ${this.id}] warmup ffmpeg: ${s}`);
|
||||
} else {
|
||||
console.log(`[cam ${this.id}] warmup ffmpeg: ${s}`);
|
||||
}
|
||||
});
|
||||
p.on('error', done);
|
||||
p.on('close', done);
|
||||
@@ -377,15 +387,24 @@ class CameraSwitch extends EventEmitter {
|
||||
count++;
|
||||
if (!best || frame.length > best.length) best = frame;
|
||||
const w = readJpegWidth(frame);
|
||||
if (count >= settleFrames && frame.length >= minSize && (w === null || w >= minWidth)) {
|
||||
decide(Buffer.from(frame), null); // kopieren: subarray teilt den Parser-Puffer
|
||||
if (count >= settleFrames) {
|
||||
if (frame.length >= minSize && (w === null || w >= minWidth)) {
|
||||
decide(Buffer.from(frame), null); // kopieren: subarray teilt den Parser-Puffer
|
||||
} else {
|
||||
console.warn(`[cam ${this.id}] hires frame ${count} verworfen: ${frame.length} bytes width=${w ?? '?'} (minSize=${minSize}, minWidth=${minWidth})`);
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
p.stdout.on('data', (c) => parser.push(c));
|
||||
p.stderr.on('data', (c) => {
|
||||
const s = c.toString();
|
||||
if (/error|busy|invalid|no such|cannot|denied/i.test(s)) console.error(`[cam ${this.id}] hires ffmpeg: ${s.trim()}`);
|
||||
const s = c.toString().trim();
|
||||
if (!s) return;
|
||||
if (/error|busy|invalid|no such|cannot|denied|input is truncated|Could not find codec parameters|Immediate exit requested|Output file is empty/i.test(s)) {
|
||||
console.warn(`[cam ${this.id}] hires ffmpeg: ${s}`);
|
||||
} else {
|
||||
console.log(`[cam ${this.id}] hires ffmpeg: ${s}`);
|
||||
}
|
||||
});
|
||||
p.on('error', (e) => { if (!decided) decide(null, e); });
|
||||
p.on('close', () => {
|
||||
|
||||
Reference in New Issue
Block a user