Web Audio Api を使用してアプリを開発しています。私は、Safari がオーディオを処理し、オーディオ コンテキストを正しくガベージ カレッジしない方法にメモリ リークがあることを発見しました。このため、新しいページをロードしたいと考えています。そのページでオーディオ コンテキストを作成し、操作を完了してからウィンドウを閉じて、メモリを解放します。
これを達成するために、次のことを行いました。
ref = window.open('record.html', '_self');
これにより、 https: //wiki.apache.org/cordova/InAppBrowser に従って、Cordova WebView で record.html ページが開きます。
1 window.open('local-url.html');// Cordova WebView にロードします
2 window.open('local-url.html', '_self');
// Cordova WebView にロードします
record.html ページは、実行したい操作を実行する JavaScript ファイルをロードします。これは、ネイティブ操作へのいくつかの呼び出しを行う recordLoad.js ファイルです (ネイティブ API は、Cordova Webview にロードされている場合にのみ使用できます。ご覧のとおり、ファイル システムにアクセスする必要があるため、これが唯一の方法です。やれ。
window.onload = createAudioContext;
ref = null;
function createAudioContext(){
console.log('createAudioContext');
window.AudioContext = window.AudioContext || window.webkitAudioContext;
navigator.getUserMedia = navigator.getUserMedia || navigator.webkitGetUserMedia;
window.URL = window.URL || window.webkitURL;
audioContext = new AudioContext;
getDirectory();
}
function getDirectory(){
console.log('getDirectory');
window.requestFileSystem(LocalFileSystem.PERSISTENT, 0, getFileSystem, fail);
}
function getFileSystem(directory){
console.log('getFileSystem');
var audioPath = localStorage.getItem('audioPath');
directory.root.getFile(audioPath, null, getVocalFile, fail);
}
function getVocalFile(fileEntry){
console.log('getVocalFile');
fileEntry.file(readVocalsToBuffer, fail);
}
function readVocalsToBuffer(file){
console.log('readVocalsToBuffer');
var reader = new FileReader();
reader.onloadend = function(evt){
var x = audioContext.decodeAudioData(evt.target._result, function(buffer){
if(!buffer){
console.log('error decoding file to Audio Buffer');
return;
}
window.voiceBuffer = buffer;
buffer = null;
loadBuffers();
});
}
reader.readAsArrayBuffer(file);
}
//web
function loadBuffers(){
console.log('loadBuffers');
var srcSong = localStorage.getItem('srcSong');
try{
var bufferLoader = new BufferLoader(
audioContext,
[
"."+srcSong
],
createOffLineContext
);
bufferLoader.load()
}
catch(e){
console.log(e.message);
}
}
//
function createOffLineContext(bufferList){
console.log('createOfflineContext');
offline = new webkitOfflineAudioContext(2, window.voiceBuffer.length, 44100);
var vocalSource = offline.createBufferSource();
vocalSource.buffer = window.voiceBuffer;
vocalSource.connect(offline.destination);
var backing = offline.createBufferSource();
backing.buffer = bufferList[0];
backing.connect(offline.destination);
vocalSource.start(0);
backing.start(0);
offline.oncomplete = function(ev){
bufferList = null;
console.log('audioContext');
console.log(audioContext);
audioContext = null;
console.log(audioContext);
vocalSource.stop(0);
backing.stop(0);
vocalSource.disconnect(0);
backing.disconnect(0);
vocalSource = null;
backing = null;
window.voiceBuffer = null;
window.renderedFile = ev.renderedBuffer;
var bufferR = ev.renderedBuffer.getChannelData(0);
var bufferL = ev.renderedBuffer.getChannelData(1);
var interleaved = interleave(bufferL, bufferR);
var dataview = encodeWAV(interleaved);
window.audioBlob = new Blob([dataview], {type: 'Wav'});
saveFile();
}
offline.startRendering();
}
// このファイルは非常に長いですが、2 つのオーディオ バッファのミキシングが完了すると、新しいファイルがファイル システムに書き込まれます。そして、その操作が完了したら、私は使用します
function gotFileWriter(writer){
console.log('gotFileWriter');
writer.onwriteend = function(evt){
console.log('onwriteEnd');
console.log(window.audioBlob);
delete window.audioBlob;
console.log(window.audioBlob);
// checkDirectory();
var ref = window.open('index.html', '_self');
// ref.addEventListener('exit', windowClose);
}
writer.write(audioBlob);
}
元の index.html ファイルに戻ります。これにより、メモリの問題が解決されます。ただし、同じ操作をもう一度実行しようとすると。つまり、record.html ファイルをロードし、recordLoad.js ファイルを実行すると、エラー ReferenceError: Can't find variable: LocalFileSystem が表示されます。
index.html をリロードすると、Cordova API へのリンクの一部が失われているように見えますが、すべてが失われているわけではありません。たとえば、Media API は使用できますが、File API は使用できません。これは、メモリ リークを解決するためのちょっとハックな方法 (ウィンドウの開閉) であることは理解していますが、それ以外の方法は見つかりません。これには本当に助けが必要です。ですから、どんな指針も大歓迎です。