Unterteilung von "Tonerkennung" in eine Klasse und einen Anwendungsteil
(EN google-translate)
(PL google-translate)
01_klassenbildung.zip - Projektdateien.
function Audiotransfer()
{
const TONDAUER_PROZ_ZYKLEN = 20; //Hiervon hängt die Geschwindigkeit der Datenübertragung ab.
const SCHWELLE = 5; //Faktor zwischen kennzahlen von gefundenem und nicht gefundenem Ton
const AUDIO_PUFFER_GROESSE = 1024;
var audiopuffer = new Array(AUDIO_PUFFER_GROESSE);
var DATA_IN = null;
var ZAEHLER = 0;
var DURCHLAUF = 0; // Anzahl Durchläaufe von prozess(e) wg. tonwechsel()
var DZ = 63;
//var DZ = 42;
//var DZ = 28;
var kennzahl = [0,0,0];
var kennzahl_phase = [63,42,28];
var signal_nummer = 0; //0==kein Signal, 1==Ton 1, 2==Ton2, 3==Ton3
//*************************************
//*** Funktionen zu Wartungszwecken ***
//*************************************
//Um den Audiopuffer zu visualiseren:
this.holeAudiopuffer = function()
{
if(DATA_IN!=null && DATA_IN.length==AUDIO_PUFFER_GROESSE)
{
for(var i=0;i<DATA_IN.length;i++)
audiopuffer[i] = DATA_IN[i];
}
return audiopuffer;
}
//..um bei langsamem Verlauf den aktuell erkannten Ton anzeigen zu können.
this.holeSignalnummer = function()
{
return signal_nummer;
}
//**************************
//*** Private Funktionen ***
//**************************
function tonwechsel()
{
if(DZ==63)
DZ=42;
else if(DZ==42)
DZ=28;
else if(DZ==28)
DZ=500; //Ungültiger Ton / Geräusch
else
DZ=63;
}
function prozess(e)
{
var data_in = e.inputBuffer.getChannelData(1);
var data_out = e.outputBuffer.getChannelData(1);
//Um den Audiopuffer zu visualiseren:
DATA_IN = data_in;
for (var i = 0; i < data_out.length; ++i)
{
if(ZAEHLER<14)
data_out[i] = 0.5;
else
data_out[i] = 0.0;
ZAEHLER++;
ZAEHLER%=DZ;
}
//Berechnung der drei Kennzahlen:
for(var k=0;k<kennzahl.length;k++)
{
kennzahl[k]=0;
var phase = kennzahl_phase[k];
var wert = 0;
for(var i=0;i<data_in.length;i++)
{
wert = data_in[i] - data_in[(i+phase)%data_in.length];
wert = wert*wert;
kennzahl[k]+=wert;
}
}
//Signalnummer aus Kennzahl bestimmen:
if(kennzahl[1]/kennzahl[0]>SCHWELLE && kennzahl[2]/kennzahl[0]>SCHWELLE)
signal_nummer = 1;
else if(kennzahl[0]/kennzahl[1]>SCHWELLE && kennzahl[2]/kennzahl[1]>SCHWELLE)
signal_nummer = 2;
else if(kennzahl[0]/kennzahl[2]>SCHWELLE && kennzahl[1]/kennzahl[2]>SCHWELLE)
signal_nummer = 3;
else
signal_nummer = 0;
if(DURCHLAUF>=TONDAUER_PROZ_ZYKLEN)
{
tonwechsel();
DURCHLAUF=0;
}
DURCHLAUF++;
}
function init(e)
{
var context = new (window.AudioContext || window.webkitAudioContext)();
var volume = context.createGain(); //Ohne Volume-Knoten bleibt der Eingang stumm!
var audioInput = context.createMediaStreamSource(e);
audioInput.connect(volume);
var node = context.createScriptProcessor(AUDIO_PUFFER_GROESSE, 2, 2);
node.onaudioprocess = function(e) { prozess(e) };
volume.connect (node);
volume.gain.value=1.0;
node.connect(context.destination);
}
//*****************************************************
//*** Funktionen der Programmierschnittstelle (API) ***
//*****************************************************
this.initialisieren = function()
{
if (!navigator.getUserMedia)
{
navigator.getUserMedia = navigator.getUserMedia || navigator.webkitGetUserMedia ||
navigator.mozGetUserMedia || navigator.msGetUserMedia;
}
if (navigator.getUserMedia)
{
//Mikrofon-Zugriff beim Benutzer anfordern
navigator.getUserMedia({audio:true}, init, function(e) {
alert('Error capturing audio.');
});
}
else
{
alert('getUserMedia not supported in this browser.');
}
}
}
Code 0-1: Klasse Audiotransfer in Datei Audiotransfer.js
<!DOCTYPE html>
<html>
<head lang="de">
<meta charset="iso-8859-1">
<script type="text/javascript" src="Audiotransfer.js"></script>
<script language:javascript>
var audiotransfer = null;
var malkontext = null;
function zeigeAudiopuffer()
{
var data_in = audiotransfer.holeAudiopuffer();
malkontext.fillStyle = "#000000";
malkontext.fillRect(0,0,1024,1000);
malkontext.strokeStyle="#ffffff";
malkontext.beginPath();
var x1 = 0;
var y1 = data_in[0]*200+200;
malkontext.moveTo(x1,y1);
for (var i = 0; i < data_in.length; i++)
{
var x2 = i;
var y2 = data_in[i]*200+200;
malkontext.lineTo(x2,y2);
}
malkontext.stroke();
document.getElementById("SIGNALNUMMER").innerHTML=audiotransfer.holeSignalnummer();
}
function initialisieren()
{
malkontext = document.getElementById("grafik").getContext("2d");
audiotransfer = new Audiotransfer();
audiotransfer.initialisieren();
setInterval(zeigeAudiopuffer,50);
}
</script>
</head>
<body onload="javascript:initialisieren()">
<canvas id="grafik" width="1024" height="400"></canvas>
<h2>Erkannt wird Signalnummer: <span id="SIGNALNUMMER"></span></h2>
</body>
</html>
Code 0-2: Anwendungsteil in Datei Teste_Audiotransfer.html