Update display audio cache (#1292)
* Use a standard map * Wrap function * Improve cache to support multiple different source arrays For the same reading/expression * Rename variable * Use null instead of an error
This commit is contained in:
parent
7fbfef513d
commit
349d9a3611
@ -79,7 +79,6 @@
|
|||||||
<script src="/mixed/js/api.js"></script>
|
<script src="/mixed/js/api.js"></script>
|
||||||
<script src="/mixed/js/japanese.js"></script>
|
<script src="/mixed/js/japanese.js"></script>
|
||||||
|
|
||||||
<script src="/mixed/js/cache-map.js"></script>
|
|
||||||
<script src="/mixed/js/document-focus-controller.js"></script>
|
<script src="/mixed/js/document-focus-controller.js"></script>
|
||||||
<script src="/mixed/js/document-util.js"></script>
|
<script src="/mixed/js/document-util.js"></script>
|
||||||
<script src="/fg/js/dom-text-scanner.js"></script>
|
<script src="/fg/js/dom-text-scanner.js"></script>
|
||||||
|
@ -93,7 +93,6 @@
|
|||||||
<script src="/mixed/js/api.js"></script>
|
<script src="/mixed/js/api.js"></script>
|
||||||
<script src="/mixed/js/japanese.js"></script>
|
<script src="/mixed/js/japanese.js"></script>
|
||||||
|
|
||||||
<script src="/mixed/js/cache-map.js"></script>
|
|
||||||
<script src="/mixed/js/document-util.js"></script>
|
<script src="/mixed/js/document-util.js"></script>
|
||||||
<script src="/fg/js/dom-text-scanner.js"></script>
|
<script src="/fg/js/dom-text-scanner.js"></script>
|
||||||
<script src="/fg/js/text-source-range.js"></script>
|
<script src="/fg/js/text-source-range.js"></script>
|
||||||
|
@ -17,7 +17,6 @@
|
|||||||
|
|
||||||
/* global
|
/* global
|
||||||
* AudioSystem
|
* AudioSystem
|
||||||
* CacheMap
|
|
||||||
* api
|
* api
|
||||||
*/
|
*/
|
||||||
|
|
||||||
@ -29,7 +28,7 @@ class DisplayAudio {
|
|||||||
this._autoPlayAudioTimer = null;
|
this._autoPlayAudioTimer = null;
|
||||||
this._autoPlayAudioDelay = 400;
|
this._autoPlayAudioDelay = 400;
|
||||||
this._eventListeners = new EventListenerCollection();
|
this._eventListeners = new EventListenerCollection();
|
||||||
this._cache = new CacheMap(32);
|
this._cache = new Map();
|
||||||
}
|
}
|
||||||
|
|
||||||
get autoPlayAudioDelay() {
|
get autoPlayAudioDelay() {
|
||||||
@ -50,6 +49,7 @@ class DisplayAudio {
|
|||||||
}
|
}
|
||||||
|
|
||||||
cleanupEntries() {
|
cleanupEntries() {
|
||||||
|
this._cache.clear();
|
||||||
this.clearAutoPlayTimer();
|
this.clearAutoPlayTimer();
|
||||||
this._eventListeners.removeAllEventListeners();
|
this._eventListeners.removeAllEventListeners();
|
||||||
}
|
}
|
||||||
@ -118,15 +118,16 @@ class DisplayAudio {
|
|||||||
try {
|
try {
|
||||||
// Create audio
|
// Create audio
|
||||||
let audio;
|
let audio;
|
||||||
let info;
|
let title;
|
||||||
try {
|
const info = await this._createExpressionAudio(sources, expression, reading, {textToSpeechVoice, customSourceUrl});
|
||||||
|
if (info !== null) {
|
||||||
let source;
|
let source;
|
||||||
({audio, source} = await this._createExpressionAudio(sources, expression, reading, {textToSpeechVoice, customSourceUrl}));
|
({audio, source} = info);
|
||||||
const sourceIndex = sources.indexOf(source);
|
const sourceIndex = sources.indexOf(source);
|
||||||
info = `From source ${1 + sourceIndex}: ${source}`;
|
title = `From source ${1 + sourceIndex}: ${source}`;
|
||||||
} catch (e) {
|
} else {
|
||||||
audio = this._audioSystem.getFallbackAudio();
|
audio = this._audioSystem.getFallbackAudio();
|
||||||
info = 'Could not find audio';
|
title = 'Could not find audio';
|
||||||
}
|
}
|
||||||
|
|
||||||
// Stop any currently playing audio
|
// Stop any currently playing audio
|
||||||
@ -135,7 +136,7 @@ class DisplayAudio {
|
|||||||
// Update details
|
// Update details
|
||||||
for (const button of this._getAudioPlayButtons(definitionIndex, expressionIndex)) {
|
for (const button of this._getAudioPlayButtons(definitionIndex, expressionIndex)) {
|
||||||
const titleDefault = button.dataset.titleDefault || '';
|
const titleDefault = button.dataset.titleDefault || '';
|
||||||
button.title = `${titleDefault}\n${info}`;
|
button.title = `${titleDefault}\n${title}`;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Play
|
// Play
|
||||||
@ -189,30 +190,43 @@ class DisplayAudio {
|
|||||||
async _createExpressionAudio(sources, expression, reading, details) {
|
async _createExpressionAudio(sources, expression, reading, details) {
|
||||||
const key = JSON.stringify([expression, reading]);
|
const key = JSON.stringify([expression, reading]);
|
||||||
|
|
||||||
const cacheValue = this._cache.get(key);
|
let sourceMap = this._cache.get(key);
|
||||||
if (typeof cacheValue !== 'undefined') {
|
if (typeof sourceMap === 'undefined') {
|
||||||
return cacheValue;
|
sourceMap = new Map();
|
||||||
|
this._cache.set(key, sourceMap);
|
||||||
}
|
}
|
||||||
|
|
||||||
for (let i = 0, ii = sources.length; i < ii; ++i) {
|
for (let i = 0, ii = sources.length; i < ii; ++i) {
|
||||||
const source = sources[i];
|
const source = sources[i];
|
||||||
const infoList = await await api.getExpressionAudioInfoList(source, expression, reading, details);
|
|
||||||
|
let infoListPromise = sourceMap.get(source);
|
||||||
|
if (typeof infoListPromise === 'undefined') {
|
||||||
|
infoListPromise = this._getExpressionAudioInfoList(source, expression, reading, details);
|
||||||
|
sourceMap.set(source, infoListPromise);
|
||||||
|
}
|
||||||
|
const infoList = await infoListPromise;
|
||||||
|
|
||||||
for (let j = 0, jj = infoList.length; j < jj; ++j) {
|
for (let j = 0, jj = infoList.length; j < jj; ++j) {
|
||||||
const info = infoList[j];
|
const item = infoList[j];
|
||||||
|
|
||||||
|
let {audioPromise} = item;
|
||||||
|
if (audioPromise === null) {
|
||||||
|
audioPromise = this._createAudioFromInfo(item.info, source);
|
||||||
|
item.audioPromise = audioPromise;
|
||||||
|
}
|
||||||
|
|
||||||
let audio;
|
let audio;
|
||||||
try {
|
try {
|
||||||
audio = await this._createAudioFromInfo(info, source);
|
audio = await audioPromise;
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
const result = {audio, source, infoList, infoListIndex: j};
|
return {audio, source, infoListIndex: j};
|
||||||
this._cache.set(key, result);
|
|
||||||
return result;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
throw new Error('Could not create audio');
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
async _createAudioFromInfo(info, source) {
|
async _createAudioFromInfo(info, source) {
|
||||||
@ -225,4 +239,9 @@ class DisplayAudio {
|
|||||||
throw new Error(`Unsupported type: ${info.type}`);
|
throw new Error(`Unsupported type: ${info.type}`);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
async _getExpressionAudioInfoList(source, expression, reading, details) {
|
||||||
|
const infoList = await api.getExpressionAudioInfoList(source, expression, reading, details);
|
||||||
|
return infoList.map((info) => ({info, audioPromise: null}));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user