diff --git a/docker-compose.yml b/docker-compose.yml
index 0bbfaf0..6236b8e 100644
--- a/docker-compose.yml
+++ b/docker-compose.yml
@@ -1,6 +1,6 @@
services:
pediatric-scribe:
- image: danielonyejesi/pediatric-ai-scribe-v3:v3.1
+ image: danielonyejesi/pediatric-ai-scribe-v3:v7
ports:
- "3552:3000"
env_file:
diff --git a/package.json b/package.json
index 7eb9c62..1b75350 100644
--- a/package.json
+++ b/package.json
@@ -1,6 +1,6 @@
{
"name": "pediatric-ai-scribe",
- "version": "3.1.0",
+ "version": "7.0.0",
"description": "AI-powered pediatric clinical documentation platform",
"main": "server.js",
"scripts": {
diff --git a/public/js/liveEncounter.js b/public/js/liveEncounter.js
index e8c0f7c..52c545b 100644
--- a/public/js/liveEncounter.js
+++ b/public/js/liveEncounter.js
@@ -20,23 +20,32 @@
var isPaused = false;
var recognition = createSpeechRecognition();
var finalText = '';
+ var sessionFinals = '';
+
+ function escHtml(s) { return String(s).replace(/&/g,'&').replace(//g,'>'); }
if (recognition) {
recognition.onresult = function(e) {
var interim = '';
for (var i = e.resultIndex; i < e.results.length; i++) {
- if (e.results[i].isFinal) finalText += e.results[i][0].transcript + ' ';
+ if (e.results[i].isFinal) sessionFinals += e.results[i][0].transcript + ' ';
else interim = e.results[i][0].transcript;
}
- transcript.innerHTML = finalText + (interim ? '' + interim + '' : '');
+ var combined = finalText + sessionFinals;
+ transcript.innerHTML = escHtml(combined) + (interim ? '' + escHtml(interim) + '' : '');
+ };
+ recognition.onend = function() {
+ finalText += sessionFinals;
+ sessionFinals = '';
+ if (isRecording && !isPaused) try { recognition.start(); } catch(e) {}
};
- recognition.onend = function() { if (isRecording && !isPaused) try { recognition.start(); } catch(e) {} };
recognition.onerror = function() {};
}
recordBtn.addEventListener('click', function() {
if (!isRecording) {
finalText = '';
+ sessionFinals = '';
recorder.start().then(function() {
isRecording = true;
isPaused = false;
@@ -63,6 +72,12 @@
showLoading('Transcribing...');
recorder.stop().then(function(blob) {
if (!blob || blob.size === 0) { hideLoading(); if (finalText.trim()) transcript.textContent = finalText.trim(); return; }
+ if (blob.size > 24 * 1024 * 1024) {
+ hideLoading();
+ transcript.textContent = finalText.trim();
+ showToast('Recording too large for AI transcription — using live transcript', 'info');
+ return;
+ }
return transcribeAudio(blob).then(function(data) {
hideLoading();
if (data.success) { transcript.textContent = data.text; showToast('Transcribed ' + dur + 's', 'success'); }
diff --git a/public/js/soap.js b/public/js/soap.js
index 61c6f7a..b33f5e5 100644
--- a/public/js/soap.js
+++ b/public/js/soap.js
@@ -18,22 +18,31 @@
var isRecording = false;
var recognition = createSpeechRecognition();
var finalText = '';
+ var sessionFinals = '';
+
+ function escHtml(s) { return String(s).replace(/&/g,'&').replace(//g,'>'); }
if (recognition) {
recognition.onresult = function(e) {
var interim = '';
for (var i = e.resultIndex; i < e.results.length; i++) {
- if (e.results[i].isFinal) finalText += e.results[i][0].transcript + ' ';
+ if (e.results[i].isFinal) sessionFinals += e.results[i][0].transcript + ' ';
else interim = e.results[i][0].transcript;
}
- transcript.innerHTML = finalText + (interim ? '' + interim + '' : '');
+ var combined = finalText + sessionFinals;
+ transcript.innerHTML = escHtml(combined) + (interim ? '' + escHtml(interim) + '' : '');
+ };
+ recognition.onend = function() {
+ finalText += sessionFinals;
+ sessionFinals = '';
+ if (isRecording) try { recognition.start(); } catch(e) {}
};
- recognition.onend = function() { if (isRecording) try { recognition.start(); } catch(e) {} };
}
recordBtn.addEventListener('click', function() {
if (!isRecording) {
finalText = '';
+ sessionFinals = '';
recorder.start().then(function() {
isRecording = true;
recordBtn.classList.add('recording');
@@ -53,6 +62,12 @@
showLoading('Transcribing...');
recorder.stop().then(function(blob) {
if (!blob) { hideLoading(); if (finalText.trim()) transcript.textContent = finalText.trim(); return; }
+ if (blob.size > 24 * 1024 * 1024) {
+ hideLoading();
+ transcript.textContent = finalText.trim();
+ showToast('Recording too large for AI transcription — using live transcript', 'info');
+ return;
+ }
return transcribeAudio(blob).then(function(data) {
hideLoading();
if (data.success) transcript.textContent = data.text;
diff --git a/public/js/voiceDictation.js b/public/js/voiceDictation.js
index 9c96633..5e50839 100644
--- a/public/js/voiceDictation.js
+++ b/public/js/voiceDictation.js
@@ -20,22 +20,31 @@
var isPaused = false;
var recognition = createSpeechRecognition();
var finalText = '';
+ var sessionFinals = '';
+
+ function escHtml(s) { return String(s).replace(/&/g,'&').replace(//g,'>'); }
if (recognition) {
recognition.onresult = function(e) {
var interim = '';
for (var i = e.resultIndex; i < e.results.length; i++) {
- if (e.results[i].isFinal) finalText += e.results[i][0].transcript + ' ';
+ if (e.results[i].isFinal) sessionFinals += e.results[i][0].transcript + ' ';
else interim = e.results[i][0].transcript;
}
- transcript.innerHTML = finalText + (interim ? '' + interim + '' : '');
+ var combined = finalText + sessionFinals;
+ transcript.innerHTML = escHtml(combined) + (interim ? '' + escHtml(interim) + '' : '');
+ };
+ recognition.onend = function() {
+ finalText += sessionFinals;
+ sessionFinals = '';
+ if (isRecording && !isPaused) try { recognition.start(); } catch(e) {}
};
- recognition.onend = function() { if (isRecording && !isPaused) try { recognition.start(); } catch(e) {} };
}
recordBtn.addEventListener('click', function() {
if (!isRecording) {
finalText = '';
+ sessionFinals = '';
recorder.start().then(function() {
isRecording = true;
isPaused = false;
@@ -61,6 +70,12 @@
showLoading('Transcribing...');
recorder.stop().then(function(blob) {
if (!blob || blob.size === 0) { hideLoading(); if (finalText.trim()) transcript.textContent = finalText.trim(); return; }
+ if (blob.size > 24 * 1024 * 1024) {
+ hideLoading();
+ transcript.textContent = finalText.trim();
+ showToast('Recording too large for AI transcription — using live transcript', 'info');
+ return;
+ }
return transcribeAudio(blob).then(function(data) {
hideLoading();
if (data.success) { transcript.textContent = data.text; showToast('Transcribed ' + dur + 's', 'success'); }