diff --git a/js/document.js b/js/document.js index 3502f52..6b4d3b4 100644 --- a/js/document.js +++ b/js/document.js @@ -285,7 +285,16 @@ function Doc(source, onEnd) { }) } - function serverDetectLanguage(text) { + async function serverDetectLanguage(text) { + try { + const service = await rxjs.firstValueFrom(fasttextObservable) + if (!service) throw new Error("FastText service unavailable") + const [prediction] = await service.sendRequest("detectLanguage", {text}) + return prediction?.language + } + catch (err) { + console.error(err) + return ajaxPost(config.serviceUrl + "/read-aloud/detect-language", {text: text}, "json") .then(JSON.parse) .then(function(res) { @@ -297,6 +306,7 @@ function Doc(source, onEnd) { console.error(err) return null }) + } } async function getSpeech(texts) { @@ -335,7 +345,7 @@ function Doc(source, onEnd) { //method getState function getState() { if (activeSpeech) return activeSpeech.getState(); - else return Promise.resolve(source.isWaiting() ? "LOADING" : "STOPPED"); + else return "LOADING" } //method getActiveSpeech diff --git a/js/messaging.js b/js/messaging.js index e3dee06..378e3cb 100644 --- a/js/messaging.js +++ b/js/messaging.js @@ -157,7 +157,7 @@ function makeDispatcher(myAddress, handlers) { if (handlers[req.method]) { Promise.resolve() .then(() => handlers[req.method](req.args, sender)) - .then(result => sendResponse({ type: "response", id: req.id, result, error: undefined }), error => sendResponse({ type: "response", id: req.id, result: undefined, error })); + .then(result => sendResponse({ to: req.from, type: "response", id: req.id, result, error: undefined }), error => sendResponse({ to: req.from, type: "response", id: req.id, result: undefined, error })); //let caller know that sendResponse will be called asynchronously return true; } @@ -187,7 +187,7 @@ function makeDispatcher(myAddress, handlers) { else pending.fulfill(res.result); } - else { + else if (res.to == myAddress) { console.error("Stray response", res); } } diff --git a/js/player.js b/js/player.js index f2345ef..e524fd1 100644 --- a/js/player.js +++ b/js/player.js @@ -14,7 +14,7 @@ const piperObservable = rxjs.defer(() => { rxjs.shareReplay({bufferSize: 1, refCount: false}) ) const piperCallbacks = new rxjs.Subject() -const domDispatcher = makeDispatcher("piper-host", { +const piperDispatcher = makeDispatcher("piper-host", { advertiseVoices({voices}, sender) { updateSettings({piperVoices: voices}) piperSubject.next(sender) @@ -25,16 +25,42 @@ const domDispatcher = makeDispatcher("piper-host", { onEnd: args => piperCallbacks.next({type: "end", ...args}), onError: args => piperCallbacks.next({type: "error", ...args}), }) + + +const fasttextSubject = new rxjs.Subject() +const fasttextObservable = rxjs.defer(() => { + createFasttextFrame() + return fasttextSubject + }) + .pipe( + rxjs.startWith(null), + rxjs.shareReplay({bufferSize: 1, refCount: false}) + ) +const fasttextDispatcher = makeDispatcher("fasttext-host", { + onServiceReady(args, sender) { + fasttextSubject.next(sender) + } +}) + + window.addEventListener("message", event => { const send = message => event.source.postMessage(message, {targetOrigin: event.origin}) - const sender = { + + piperDispatcher.dispatch(event.data, { sendRequest(method, args) { const id = String(Math.random()) - send({to: "piper-service", type: "request", id, method, args}) - return domDispatcher.waitForResponse(id) + send({from: "piper-host", to: "piper-service", type: "request", id, method, args}) + return piperDispatcher.waitForResponse(id) } - } - domDispatcher.dispatch(event.data, sender, send) + }, send) + + fasttextDispatcher.dispatch(event.data, { + sendRequest(method, args) { + const id = String(Math.random()) + send({from: "fasttext-host", to: "fasttext-service", type: "request", id, method, args}) + return fasttextDispatcher.waitForResponse(id) + } + }, send) }) @@ -346,3 +372,12 @@ function createPiperFrame() { f.style.borderWidth = "0" document.body.appendChild(f) } + +function createFasttextFrame() { + const f = document.createElement("iframe") + f.id = "fasttext-frame" + f.src = "https://ttstool.com/fasttext/index.html" + f.allow = "cross-origin-isolated" + f.style.display = "none" + document.body.appendChild(f) +}